2 * OSPF Sending and Receiving OSPF Packets.
3 * Copyright (C) 1999, 2000 Toshiaki Takada
5 * This file is part of GNU Zebra.
7 * GNU Zebra is free software; you can redistribute it and/or modify it
8 * under the terms of the GNU General Public License as published by the
9 * Free Software Foundation; either version 2, or (at your option) any
12 * GNU Zebra is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty of
14 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
15 * General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with GNU Zebra; see the file COPYING. If not, write to the Free
19 * Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
31 #include "sockunion.h"
37 #include "ospfd/ospfd.h"
38 #include "ospfd/ospf_network.h"
39 #include "ospfd/ospf_interface.h"
40 #include "ospfd/ospf_ism.h"
41 #include "ospfd/ospf_asbr.h"
42 #include "ospfd/ospf_lsa.h"
43 #include "ospfd/ospf_lsdb.h"
44 #include "ospfd/ospf_neighbor.h"
45 #include "ospfd/ospf_nsm.h"
46 #include "ospfd/ospf_packet.h"
47 #include "ospfd/ospf_spf.h"
48 #include "ospfd/ospf_flood.h"
49 #include "ospfd/ospf_dump.h"
51 static void ospf_ls_ack_send_list (struct ospf_interface
*, struct list
*,
54 /* Packet Type String. */
55 const char *ospf_packet_type_str
[] =
59 "Database Description",
62 "Link State Acknowledgment",
65 extern int in_cksum (void *ptr
, int nbytes
);
67 /* OSPF authentication checking function */
69 ospf_auth_type (struct ospf_interface
*oi
)
73 if (OSPF_IF_PARAM (oi
, auth_type
) == OSPF_AUTH_NOTSET
)
74 auth_type
= oi
->area
->auth_type
;
76 auth_type
= OSPF_IF_PARAM (oi
, auth_type
);
78 /* Handle case where MD5 key list is not configured aka Cisco */
79 if (auth_type
== OSPF_AUTH_CRYPTOGRAPHIC
&&
80 list_isempty (OSPF_IF_PARAM (oi
, auth_crypt
)))
81 return OSPF_AUTH_NULL
;
88 ospf_packet_new (size_t size
)
90 struct ospf_packet
*new;
92 new = XCALLOC (MTYPE_OSPF_PACKET
, sizeof (struct ospf_packet
));
93 new->s
= stream_new (size
);
99 ospf_packet_free (struct ospf_packet
*op
)
104 XFREE (MTYPE_OSPF_PACKET
, op
);
112 struct ospf_fifo
*new;
114 new = XCALLOC (MTYPE_OSPF_FIFO
, sizeof (struct ospf_fifo
));
118 /* Add new packet to fifo. */
120 ospf_fifo_push (struct ospf_fifo
*fifo
, struct ospf_packet
*op
)
123 fifo
->tail
->next
= op
;
132 /* Delete first packet from fifo. */
134 ospf_fifo_pop (struct ospf_fifo
*fifo
)
136 struct ospf_packet
*op
;
142 fifo
->head
= op
->next
;
144 if (fifo
->head
== NULL
)
153 /* Return first fifo entry. */
155 ospf_fifo_head (struct ospf_fifo
*fifo
)
160 /* Flush ospf packet fifo. */
162 ospf_fifo_flush (struct ospf_fifo
*fifo
)
164 struct ospf_packet
*op
;
165 struct ospf_packet
*next
;
167 for (op
= fifo
->head
; op
; op
= next
)
170 ospf_packet_free (op
);
172 fifo
->head
= fifo
->tail
= NULL
;
176 /* Free ospf packet fifo. */
178 ospf_fifo_free (struct ospf_fifo
*fifo
)
180 ospf_fifo_flush (fifo
);
182 XFREE (MTYPE_OSPF_FIFO
, fifo
);
186 ospf_packet_add (struct ospf_interface
*oi
, struct ospf_packet
*op
)
190 zlog_err("ospf_packet_add(interface %s in state %d [%s], packet type %s, "
191 "destination %s) called with NULL obuf, ignoring "
192 "(please report this bug)!\n",
193 IF_NAME(oi
), oi
->state
, LOOKUP (ospf_ism_state_msg
, oi
->state
),
194 ospf_packet_type_str
[stream_getc_from(op
->s
, 1)],
195 inet_ntoa (op
->dst
));
199 /* Add packet to end of queue. */
200 ospf_fifo_push (oi
->obuf
, op
);
202 /* Debug of packet fifo*/
203 /* ospf_fifo_debug (oi->obuf); */
207 ospf_packet_delete (struct ospf_interface
*oi
)
209 struct ospf_packet
*op
;
211 op
= ospf_fifo_pop (oi
->obuf
);
214 ospf_packet_free (op
);
218 ospf_packet_dup (struct ospf_packet
*op
)
220 struct ospf_packet
*new;
222 if (stream_get_endp(op
->s
) != op
->length
)
223 zlog_warn ("ospf_packet_dup stream %ld ospf_packet %d size mismatch",
224 STREAM_SIZE(op
->s
), op
->length
);
226 /* Reserve space for MD5 authentication that may be added later. */
227 new = ospf_packet_new (stream_get_endp(op
->s
) + OSPF_AUTH_MD5_SIZE
);
228 stream_copy (new->s
, op
->s
);
231 new->length
= op
->length
;
238 ospf_packet_authspace (struct ospf_interface
*oi
)
242 if ( ospf_auth_type (oi
) == OSPF_AUTH_CRYPTOGRAPHIC
)
243 auth
= OSPF_AUTH_MD5_SIZE
;
249 ospf_packet_max (struct ospf_interface
*oi
)
253 max
= oi
->ifp
->mtu
- ospf_packet_authspace(oi
);
255 max
-= (OSPF_HEADER_SIZE
+ sizeof (struct ip
));
262 ospf_check_md5_digest (struct ospf_interface
*oi
, struct stream
*s
,
267 unsigned char digest
[OSPF_AUTH_MD5_SIZE
];
268 unsigned char *pdigest
;
269 struct crypt_key
*ck
;
270 struct ospf_header
*ospfh
;
271 struct ospf_neighbor
*nbr
;
274 ibuf
= STREAM_PNT (s
);
275 ospfh
= (struct ospf_header
*) ibuf
;
277 /* Get pointer to the end of the packet. */
278 pdigest
= ibuf
+ length
;
280 /* Get secret key. */
281 ck
= ospf_crypt_key_lookup (OSPF_IF_PARAM (oi
, auth_crypt
),
282 ospfh
->u
.crypt
.key_id
);
285 zlog_warn ("interface %s: ospf_check_md5 no key %d",
286 IF_NAME (oi
), ospfh
->u
.crypt
.key_id
);
290 /* check crypto seqnum. */
291 nbr
= ospf_nbr_lookup_by_routerid (oi
->nbrs
, &ospfh
->router_id
);
293 if (nbr
&& ntohl(nbr
->crypt_seqnum
) > ntohl(ospfh
->u
.crypt
.crypt_seqnum
))
295 zlog_warn ("interface %s: ospf_check_md5 bad sequence %d (expect %d)",
297 ntohl(ospfh
->u
.crypt
.crypt_seqnum
),
298 ntohl(nbr
->crypt_seqnum
));
302 /* Generate a digest for the ospf packet - their digest + our digest. */
304 md5_process_bytes (ibuf
, length
, &ctx
);
305 md5_process_bytes (ck
->auth_key
, OSPF_AUTH_MD5_SIZE
, &ctx
);
306 md5_finish_ctx (&ctx
, digest
);
308 /* compare the two */
309 if (memcmp (pdigest
, digest
, OSPF_AUTH_MD5_SIZE
))
311 zlog_warn ("interface %s: ospf_check_md5 checksum mismatch",
316 /* save neighbor's crypt_seqnum */
318 nbr
->crypt_seqnum
= ospfh
->u
.crypt
.crypt_seqnum
;
322 /* This function is called from ospf_write(), it will detect the
323 authentication scheme and if it is MD5, it will change the sequence
324 and update the MD5 digest. */
326 ospf_make_md5_digest (struct ospf_interface
*oi
, struct ospf_packet
*op
)
328 struct ospf_header
*ospfh
;
329 unsigned char digest
[OSPF_AUTH_MD5_SIZE
];
333 struct crypt_key
*ck
;
336 ibuf
= STREAM_DATA (op
->s
);
337 ospfh
= (struct ospf_header
*) ibuf
;
339 if (ntohs (ospfh
->auth_type
) != OSPF_AUTH_CRYPTOGRAPHIC
)
342 /* We do this here so when we dup a packet, we don't have to
343 waste CPU rewriting other headers. */
344 t
= (time(NULL
) & 0xFFFFFFFF);
345 oi
->crypt_seqnum
= ( t
> oi
->crypt_seqnum
? t
: oi
->crypt_seqnum
++);
346 ospfh
->u
.crypt
.crypt_seqnum
= htonl (oi
->crypt_seqnum
);
348 /* Get MD5 Authentication key from auth_key list. */
349 if (list_isempty (OSPF_IF_PARAM (oi
, auth_crypt
)))
350 auth_key
= (char *) "";
353 ck
= listgetdata (listtail(OSPF_IF_PARAM (oi
, auth_crypt
)));
354 auth_key
= (char *) ck
->auth_key
;
357 /* Generate a digest for the entire packet + our secret key. */
359 md5_process_bytes (ibuf
, ntohs (ospfh
->length
), &ctx
);
360 md5_process_bytes (auth_key
, OSPF_AUTH_MD5_SIZE
, &ctx
);
361 md5_finish_ctx (&ctx
, digest
);
363 /* Append md5 digest to the end of the stream. */
364 stream_put (op
->s
, digest
, OSPF_AUTH_MD5_SIZE
);
366 /* We do *NOT* increment the OSPF header length. */
367 op
->length
= ntohs (ospfh
->length
) + OSPF_AUTH_MD5_SIZE
;
369 if (stream_get_endp(op
->s
) != op
->length
)
370 zlog_warn("ospf_make_md5_digest: length mismatch stream %ld ospf_packet %d", stream_get_endp(op
->s
), op
->length
);
372 return OSPF_AUTH_MD5_SIZE
;
377 ospf_ls_req_timer (struct thread
*thread
)
379 struct ospf_neighbor
*nbr
;
381 nbr
= THREAD_ARG (thread
);
382 nbr
->t_ls_req
= NULL
;
384 /* Send Link State Request. */
385 if (ospf_ls_request_count (nbr
))
386 ospf_ls_req_send (nbr
);
388 /* Set Link State Request retransmission timer. */
389 OSPF_NSM_TIMER_ON (nbr
->t_ls_req
, ospf_ls_req_timer
, nbr
->v_ls_req
);
395 ospf_ls_req_event (struct ospf_neighbor
*nbr
)
399 thread_cancel (nbr
->t_ls_req
);
400 nbr
->t_ls_req
= NULL
;
402 nbr
->t_ls_req
= thread_add_event (master
, ospf_ls_req_timer
, nbr
, 0);
405 /* Cyclic timer function. Fist registered in ospf_nbr_new () in
408 ospf_ls_upd_timer (struct thread
*thread
)
410 struct ospf_neighbor
*nbr
;
412 nbr
= THREAD_ARG (thread
);
413 nbr
->t_ls_upd
= NULL
;
415 /* Send Link State Update. */
416 if (ospf_ls_retransmit_count (nbr
) > 0)
419 struct ospf_lsdb
*lsdb
;
422 int retransmit_interval
;
424 gettimeofday (&now
, NULL
);
425 retransmit_interval
= OSPF_IF_PARAM (nbr
->oi
, retransmit_interval
);
427 lsdb
= &nbr
->ls_rxmt
;
428 update
= list_new ();
430 for (i
= OSPF_MIN_LSA
; i
< OSPF_MAX_LSA
; i
++)
432 struct route_table
*table
= lsdb
->type
[i
].db
;
433 struct route_node
*rn
;
435 for (rn
= route_top (table
); rn
; rn
= route_next (rn
))
437 struct ospf_lsa
*lsa
;
439 if ((lsa
= rn
->info
) != NULL
)
440 /* Don't retransmit an LSA if we received it within
441 the last RxmtInterval seconds - this is to allow the
442 neighbour a chance to acknowledge the LSA as it may
443 have ben just received before the retransmit timer
444 fired. This is a small tweak to what is in the RFC,
445 but it will cut out out a lot of retransmit traffic
447 if (tv_cmp (tv_sub (now
, lsa
->tv_recv
),
448 int2tv (retransmit_interval
)) >= 0)
449 listnode_add (update
, rn
->info
);
453 if (listcount (update
) > 0)
454 ospf_ls_upd_send (nbr
, update
, OSPF_SEND_PACKET_DIRECT
);
455 list_delete (update
);
458 /* Set LS Update retransmission timer. */
459 OSPF_NSM_TIMER_ON (nbr
->t_ls_upd
, ospf_ls_upd_timer
, nbr
->v_ls_upd
);
465 ospf_ls_ack_timer (struct thread
*thread
)
467 struct ospf_interface
*oi
;
469 oi
= THREAD_ARG (thread
);
472 /* Send Link State Acknowledgment. */
473 if (listcount (oi
->ls_ack
) > 0)
474 ospf_ls_ack_send_delayed (oi
);
476 /* Set LS Ack timer. */
477 OSPF_ISM_TIMER_ON (oi
->t_ls_ack
, ospf_ls_ack_timer
, oi
->v_ls_ack
);
482 #ifdef WANT_OSPF_WRITE_FRAGMENT
484 ospf_write_frags (int fd
, struct ospf_packet
*op
, struct ip
*iph
,
485 struct msghdr
*msg
, unsigned int maxdatasize
,
486 unsigned int mtu
, int flags
, u_char type
)
488 #define OSPF_WRITE_FRAG_SHIFT 3
493 assert ( op
->length
== stream_get_endp(op
->s
) );
494 assert (msg
->msg_iovlen
== 2);
498 * SunOS, BSD and BSD derived kernels likely will clear ip_id, as
499 * well as the IP_MF flag, making this all quite pointless.
501 * However, for a system on which IP_MF is left alone, and ip_id left
502 * alone or else which sets same ip_id for each fragment this might
505 * XXX-TODO: It would be much nicer to have the kernel's use their
506 * existing fragmentation support to do this for us. Bugs/RFEs need to
507 * be raised against the various kernels.
511 iph
->ip_off
|= IP_MF
;
513 /* ip frag offset is expressed in units of 8byte words */
514 offset
= maxdatasize
>> OSPF_WRITE_FRAG_SHIFT
;
516 iovp
= &msg
->msg_iov
[1];
518 while ( (stream_get_endp(op
->s
) - stream_get_getp (op
->s
))
521 /* data length of this frag is to next offset value */
522 iovp
->iov_len
= offset
<< OSPF_WRITE_FRAG_SHIFT
;
523 iph
->ip_len
= iovp
->iov_len
+ sizeof (struct ip
);
524 assert (iph
->ip_len
<= mtu
);
526 sockopt_iphdrincl_swab_htosys (iph
);
528 ret
= sendmsg (fd
, msg
, flags
);
530 sockopt_iphdrincl_swab_systoh (iph
);
533 zlog_warn ("*** ospf_write_frags: sendmsg failed to %s,"
534 " id %d, off %d, len %d, mtu %u failed with %s",
535 inet_ntoa (iph
->ip_dst
),
540 safe_strerror (errno
));
542 if (IS_DEBUG_OSPF_PACKET (type
- 1, SEND
))
544 zlog_debug ("ospf_write_frags: sent id %d, off %d, len %d to %s\n",
545 iph
->ip_id
, iph
->ip_off
, iph
->ip_len
,
546 inet_ntoa (iph
->ip_dst
));
547 if (IS_DEBUG_OSPF_PACKET (type
- 1, DETAIL
))
549 zlog_debug ("-----------------IP Header Dump----------------------");
550 ospf_ip_header_dump (iph
);
551 zlog_debug ("-----------------------------------------------------");
555 iph
->ip_off
+= offset
;
556 stream_forward_getp (op
->s
, iovp
->iov_len
);
557 iovp
->iov_base
= STREAM_PNT (op
->s
);
560 /* setup for final fragment */
561 iovp
->iov_len
= stream_get_endp(op
->s
) - stream_get_getp (op
->s
);
562 iph
->ip_len
= iovp
->iov_len
+ sizeof (struct ip
);
563 iph
->ip_off
&= (~IP_MF
);
565 #endif /* WANT_OSPF_WRITE_FRAGMENT */
568 ospf_write (struct thread
*thread
)
570 struct ospf
*ospf
= THREAD_ARG (thread
);
571 struct ospf_interface
*oi
;
572 struct ospf_packet
*op
;
573 struct sockaddr_in sa_dst
;
580 struct listnode
*node
;
581 #ifdef WANT_OSPF_WRITE_FRAGMENT
582 static u_int16_t ipid
= 0;
583 #endif /* WANT_OSPF_WRITE_FRAGMENT */
584 u_int16_t maxdatasize
;
585 #define OSPF_WRITE_IPHL_SHIFT 2
587 ospf
->t_write
= NULL
;
589 node
= listhead (ospf
->oi_write_q
);
591 oi
= listgetdata (node
);
594 #ifdef WANT_OSPF_WRITE_FRAGMENT
595 /* seed ipid static with low order bits of time */
597 ipid
= (time(NULL
) & 0xffff);
598 #endif /* WANT_OSPF_WRITE_FRAGMENT */
600 /* convenience - max OSPF data per packet */
601 maxdatasize
= oi
->ifp
->mtu
- sizeof (struct ip
);
603 /* Get one packet from queue. */
604 op
= ospf_fifo_head (oi
->obuf
);
606 assert (op
->length
>= OSPF_HEADER_SIZE
);
608 if (op
->dst
.s_addr
== htonl (OSPF_ALLSPFROUTERS
)
609 || op
->dst
.s_addr
== htonl (OSPF_ALLDROUTERS
))
610 ospf_if_ipmulticast (ospf
, oi
->address
, oi
->ifp
->ifindex
);
612 /* Rewrite the md5 signature & update the seq */
613 ospf_make_md5_digest (oi
, op
);
615 /* Retrieve OSPF packet type. */
616 stream_set_getp (op
->s
, 1);
617 type
= stream_getc (op
->s
);
619 /* reset get pointer */
620 stream_set_getp (op
->s
, 0);
622 memset (&iph
, 0, sizeof (struct ip
));
623 memset (&sa_dst
, 0, sizeof (sa_dst
));
625 sa_dst
.sin_family
= AF_INET
;
627 sa_dst
.sin_len
= sizeof(sa_dst
);
628 #endif /* HAVE_SIN_LEN */
629 sa_dst
.sin_addr
= op
->dst
;
630 sa_dst
.sin_port
= htons (0);
632 /* Set DONTROUTE flag if dst is unicast. */
633 if (oi
->type
!= OSPF_IFTYPE_VIRTUALLINK
)
634 if (!IN_MULTICAST (htonl (op
->dst
.s_addr
)))
635 flags
= MSG_DONTROUTE
;
637 iph
.ip_hl
= sizeof (struct ip
) >> OSPF_WRITE_IPHL_SHIFT
;
638 /* it'd be very strange for header to not be 4byte-word aligned but.. */
639 if ( sizeof (struct ip
)
640 > (unsigned int)(iph
.ip_hl
<< OSPF_WRITE_IPHL_SHIFT
) )
641 iph
.ip_hl
++; /* we presume sizeof struct ip cant overflow ip_hl.. */
643 iph
.ip_v
= IPVERSION
;
644 iph
.ip_tos
= IPTOS_PREC_INTERNETCONTROL
;
645 iph
.ip_len
= (iph
.ip_hl
<< OSPF_WRITE_IPHL_SHIFT
) + op
->length
;
647 #ifdef WANT_OSPF_WRITE_FRAGMENT
648 /* XXX-MT: not thread-safe at all..
649 * XXX: this presumes this is only programme sending OSPF packets
650 * otherwise, no guarantee ipid will be unique
653 #endif /* WANT_OSPF_WRITE_FRAGMENT */
656 if (oi
->type
== OSPF_IFTYPE_VIRTUALLINK
)
657 iph
.ip_ttl
= OSPF_VL_IP_TTL
;
659 iph
.ip_ttl
= OSPF_IP_TTL
;
660 iph
.ip_p
= IPPROTO_OSPFIGP
;
662 iph
.ip_src
.s_addr
= oi
->address
->u
.prefix4
.s_addr
;
663 iph
.ip_dst
.s_addr
= op
->dst
.s_addr
;
665 memset (&msg
, 0, sizeof (msg
));
666 msg
.msg_name
= (caddr_t
) &sa_dst
;
667 msg
.msg_namelen
= sizeof (sa_dst
);
670 iov
[0].iov_base
= (char*)&iph
;
671 iov
[0].iov_len
= iph
.ip_hl
<< OSPF_WRITE_IPHL_SHIFT
;
672 iov
[1].iov_base
= STREAM_PNT (op
->s
);
673 iov
[1].iov_len
= op
->length
;
675 /* Sadly we can not rely on kernels to fragment packets because of either
676 * IP_HDRINCL and/or multicast destination being set.
678 #ifdef WANT_OSPF_WRITE_FRAGMENT
679 if ( op
->length
> maxdatasize
)
680 ospf_write_frags (ospf
->fd
, op
, &iph
, &msg
, maxdatasize
,
681 oi
->ifp
->mtu
, flags
, type
);
682 #endif /* WANT_OSPF_WRITE_FRAGMENT */
684 /* send final fragment (could be first) */
685 sockopt_iphdrincl_swab_htosys (&iph
);
686 ret
= sendmsg (ospf
->fd
, &msg
, flags
);
687 sockopt_iphdrincl_swab_systoh (&iph
);
690 zlog_warn ("*** sendmsg in ospf_write failed to %s, "
691 "id %d, off %d, len %d, interface %s, mtu %u: %s",
692 inet_ntoa (iph
.ip_dst
), iph
.ip_id
, iph
.ip_off
, iph
.ip_len
,
693 oi
->ifp
->name
, oi
->ifp
->mtu
, safe_strerror (errno
));
695 /* Show debug sending packet. */
696 if (IS_DEBUG_OSPF_PACKET (type
- 1, SEND
))
698 if (IS_DEBUG_OSPF_PACKET (type
- 1, DETAIL
))
700 zlog_debug ("-----------------------------------------------------");
701 ospf_ip_header_dump (&iph
);
702 stream_set_getp (op
->s
, 0);
703 ospf_packet_dump (op
->s
);
706 zlog_debug ("%s sent to [%s] via [%s].",
707 ospf_packet_type_str
[type
], inet_ntoa (op
->dst
),
710 if (IS_DEBUG_OSPF_PACKET (type
- 1, DETAIL
))
711 zlog_debug ("-----------------------------------------------------");
714 /* Now delete packet from queue. */
715 ospf_packet_delete (oi
);
717 if (ospf_fifo_head (oi
->obuf
) == NULL
)
720 list_delete_node (ospf
->oi_write_q
, node
);
723 /* If packets still remain in queue, call write thread. */
724 if (!list_isempty (ospf
->oi_write_q
))
726 thread_add_write (master
, ospf_write
, ospf
, ospf
->fd
);
731 /* OSPF Hello message read -- RFC2328 Section 10.5. */
733 ospf_hello (struct ip
*iph
, struct ospf_header
*ospfh
,
734 struct stream
* s
, struct ospf_interface
*oi
, int size
)
736 struct ospf_hello
*hello
;
737 struct ospf_neighbor
*nbr
;
741 /* increment statistics. */
744 hello
= (struct ospf_hello
*) STREAM_PNT (s
);
746 /* If Hello is myself, silently discard. */
747 if (IPV4_ADDR_SAME (&ospfh
->router_id
, &oi
->ospf
->router_id
))
749 if (IS_DEBUG_OSPF_PACKET (ospfh
->type
- 1, RECV
))
751 zlog_debug ("ospf_header[%s/%s]: selforiginated, "
753 ospf_packet_type_str
[ospfh
->type
],
754 inet_ntoa (iph
->ip_src
));
759 /* If incoming interface is passive one, ignore Hello. */
760 if (OSPF_IF_PARAM (oi
, passive_interface
) == OSPF_IF_PASSIVE
) {
761 char buf
[3][INET_ADDRSTRLEN
];
762 zlog_warn("Warning: ignoring HELLO from router %s sent to %s; we "
763 "should not receive hellos on passive interface %s!",
764 inet_ntop(AF_INET
, &ospfh
->router_id
, buf
[0], sizeof(buf
[0])),
765 inet_ntop(AF_INET
, &iph
->ip_dst
, buf
[1], sizeof(buf
[1])),
766 inet_ntop(AF_INET
, &oi
->address
->u
.prefix4
,
767 buf
[2], sizeof(buf
[2])));
768 if (iph
->ip_dst
.s_addr
== htonl(OSPF_ALLSPFROUTERS
))
770 /* Try to fix multicast membership. */
771 SET_FLAG(oi
->multicast_memberships
, MEMBER_ALLROUTERS
);
772 ospf_if_set_multicast(oi
);
777 /* get neighbor prefix. */
779 p
.prefixlen
= ip_masklen (hello
->network_mask
);
780 p
.u
.prefix4
= iph
->ip_src
;
782 /* Compare network mask. */
783 /* Checking is ignored for Point-to-Point and Virtual link. */
784 if (oi
->type
!= OSPF_IFTYPE_POINTOPOINT
785 && oi
->type
!= OSPF_IFTYPE_VIRTUALLINK
)
786 if (oi
->address
->prefixlen
!= p
.prefixlen
)
788 zlog_warn ("Packet %s [Hello:RECV]: NetworkMask mismatch.",
789 inet_ntoa (ospfh
->router_id
));
793 /* Compare Hello Interval. */
794 if (OSPF_IF_PARAM (oi
, v_hello
) != ntohs (hello
->hello_interval
))
796 zlog_warn ("Packet %s [Hello:RECV]: HelloInterval mismatch.",
797 inet_ntoa (ospfh
->router_id
));
801 /* Compare Router Dead Interval. */
802 if (OSPF_IF_PARAM (oi
, v_wait
) != ntohl (hello
->dead_interval
))
804 zlog_warn ("Packet %s [Hello:RECV]: RouterDeadInterval mismatch.",
805 inet_ntoa (ospfh
->router_id
));
809 if (IS_DEBUG_OSPF_EVENT
)
810 zlog_debug ("Packet %s [Hello:RECV]: Options %s",
811 inet_ntoa (ospfh
->router_id
),
812 ospf_options_dump (hello
->options
));
814 /* Compare options. */
815 #define REJECT_IF_TBIT_ON 1 /* XXX */
816 #ifdef REJECT_IF_TBIT_ON
817 if (CHECK_FLAG (hello
->options
, OSPF_OPTION_T
))
820 * This router does not support non-zero TOS.
821 * Drop this Hello packet not to establish neighbor relationship.
823 zlog_warn ("Packet %s [Hello:RECV]: T-bit on, drop it.",
824 inet_ntoa (ospfh
->router_id
));
827 #endif /* REJECT_IF_TBIT_ON */
829 #ifdef HAVE_OPAQUE_LSA
830 if (CHECK_FLAG (oi
->ospf
->config
, OSPF_OPAQUE_CAPABLE
)
831 && CHECK_FLAG (hello
->options
, OSPF_OPTION_O
))
834 * This router does know the correct usage of O-bit
835 * the bit should be set in DD packet only.
837 zlog_warn ("Packet %s [Hello:RECV]: O-bit abuse?",
838 inet_ntoa (ospfh
->router_id
));
839 #ifdef STRICT_OBIT_USAGE_CHECK
840 return; /* Reject this packet. */
841 #else /* STRICT_OBIT_USAGE_CHECK */
842 UNSET_FLAG (hello
->options
, OSPF_OPTION_O
); /* Ignore O-bit. */
843 #endif /* STRICT_OBIT_USAGE_CHECK */
845 #endif /* HAVE_OPAQUE_LSA */
847 /* new for NSSA is to ensure that NP is on and E is off */
849 if (oi
->area
->external_routing
== OSPF_AREA_NSSA
)
851 if (! (CHECK_FLAG (OPTIONS (oi
), OSPF_OPTION_NP
)
852 && CHECK_FLAG (hello
->options
, OSPF_OPTION_NP
)
853 && ! CHECK_FLAG (OPTIONS (oi
), OSPF_OPTION_E
)
854 && ! CHECK_FLAG (hello
->options
, OSPF_OPTION_E
)))
856 zlog_warn ("NSSA-Packet-%s[Hello:RECV]: my options: %x, his options %x", inet_ntoa (ospfh
->router_id
), OPTIONS (oi
), hello
->options
);
859 if (IS_DEBUG_OSPF_NSSA
)
860 zlog_debug ("NSSA-Hello:RECV:Packet from %s:", inet_ntoa(ospfh
->router_id
));
863 /* The setting of the E-bit found in the Hello Packet's Options
864 field must match this area's ExternalRoutingCapability A
865 mismatch causes processing to stop and the packet to be
866 dropped. The setting of the rest of the bits in the Hello
867 Packet's Options field should be ignored. */
868 if (CHECK_FLAG (OPTIONS (oi
), OSPF_OPTION_E
) !=
869 CHECK_FLAG (hello
->options
, OSPF_OPTION_E
))
871 zlog_warn ("Packet %s [Hello:RECV]: my options: %x, his options %x",
872 inet_ntoa(ospfh
->router_id
), OPTIONS (oi
), hello
->options
);
876 /* get neighbour struct */
877 nbr
= ospf_nbr_get (oi
, ospfh
, iph
, &p
);
879 /* neighbour must be valid, ospf_nbr_get creates if none existed */
882 old_state
= nbr
->state
;
884 /* Add event to thread. */
885 OSPF_NSM_EVENT_EXECUTE (nbr
, NSM_HelloReceived
);
887 /* RFC2328 Section 9.5.1
888 If the router is not eligible to become Designated Router,
889 (snip) It must also send an Hello Packet in reply to an
890 Hello Packet received from any eligible neighbor (other than
891 the current Designated Router and Backup Designated Router). */
892 if (oi
->type
== OSPF_IFTYPE_NBMA
)
893 if (PRIORITY(oi
) == 0 && hello
->priority
> 0
894 && IPV4_ADDR_CMP(&DR(oi
), &iph
->ip_src
)
895 && IPV4_ADDR_CMP(&BDR(oi
), &iph
->ip_src
))
896 OSPF_NSM_TIMER_ON (nbr
->t_hello_reply
, ospf_hello_reply_timer
,
897 OSPF_HELLO_REPLY_DELAY
);
899 /* on NBMA network type, it happens to receive bidirectional Hello packet
900 without advance 1-Way Received event.
901 To avoid incorrect DR-seletion, raise 1-Way Received event.*/
902 if (oi
->type
== OSPF_IFTYPE_NBMA
&&
903 (old_state
== NSM_Down
|| old_state
== NSM_Attempt
))
905 OSPF_NSM_EVENT_EXECUTE (nbr
, NSM_OneWayReceived
);
906 nbr
->priority
= hello
->priority
;
907 nbr
->d_router
= hello
->d_router
;
908 nbr
->bd_router
= hello
->bd_router
;
912 if (ospf_nbr_bidirectional (&oi
->ospf
->router_id
, hello
->neighbors
,
913 size
- OSPF_HELLO_MIN_SIZE
))
915 OSPF_NSM_EVENT_EXECUTE (nbr
, NSM_TwoWayReceived
);
916 nbr
->options
|= hello
->options
;
920 OSPF_NSM_EVENT_EXECUTE (nbr
, NSM_OneWayReceived
);
921 /* Set neighbor information. */
922 nbr
->priority
= hello
->priority
;
923 nbr
->d_router
= hello
->d_router
;
924 nbr
->bd_router
= hello
->bd_router
;
928 /* If neighbor itself declares DR and no BDR exists,
929 cause event BackupSeen */
930 if (IPV4_ADDR_SAME (&nbr
->address
.u
.prefix4
, &hello
->d_router
))
931 if (hello
->bd_router
.s_addr
== 0 && oi
->state
== ISM_Waiting
)
932 OSPF_ISM_EVENT_SCHEDULE (oi
, ISM_BackupSeen
);
934 /* neighbor itself declares BDR. */
935 if (oi
->state
== ISM_Waiting
&&
936 IPV4_ADDR_SAME (&nbr
->address
.u
.prefix4
, &hello
->bd_router
))
937 OSPF_ISM_EVENT_SCHEDULE (oi
, ISM_BackupSeen
);
939 /* had not previously. */
940 if ((IPV4_ADDR_SAME (&nbr
->address
.u
.prefix4
, &hello
->d_router
) &&
941 IPV4_ADDR_CMP (&nbr
->address
.u
.prefix4
, &nbr
->d_router
)) ||
942 (IPV4_ADDR_CMP (&nbr
->address
.u
.prefix4
, &hello
->d_router
) &&
943 IPV4_ADDR_SAME (&nbr
->address
.u
.prefix4
, &nbr
->d_router
)))
944 OSPF_ISM_EVENT_SCHEDULE (oi
, ISM_NeighborChange
);
946 /* had not previously. */
947 if ((IPV4_ADDR_SAME (&nbr
->address
.u
.prefix4
, &hello
->bd_router
) &&
948 IPV4_ADDR_CMP (&nbr
->address
.u
.prefix4
, &nbr
->bd_router
)) ||
949 (IPV4_ADDR_CMP (&nbr
->address
.u
.prefix4
, &hello
->bd_router
) &&
950 IPV4_ADDR_SAME (&nbr
->address
.u
.prefix4
, &nbr
->bd_router
)))
951 OSPF_ISM_EVENT_SCHEDULE (oi
, ISM_NeighborChange
);
953 /* Neighbor priority check. */
954 if (nbr
->priority
>= 0 && nbr
->priority
!= hello
->priority
)
955 OSPF_ISM_EVENT_SCHEDULE (oi
, ISM_NeighborChange
);
957 /* Set neighbor information. */
958 nbr
->priority
= hello
->priority
;
959 nbr
->d_router
= hello
->d_router
;
960 nbr
->bd_router
= hello
->bd_router
;
963 /* Save DD flags/options/Seqnum received. */
965 ospf_db_desc_save_current (struct ospf_neighbor
*nbr
,
966 struct ospf_db_desc
*dd
)
968 nbr
->last_recv
.flags
= dd
->flags
;
969 nbr
->last_recv
.options
= dd
->options
;
970 nbr
->last_recv
.dd_seqnum
= ntohl (dd
->dd_seqnum
);
973 /* Process rest of DD packet. */
975 ospf_db_desc_proc (struct stream
*s
, struct ospf_interface
*oi
,
976 struct ospf_neighbor
*nbr
, struct ospf_db_desc
*dd
,
979 struct ospf_lsa
*new, *find
;
980 struct lsa_header
*lsah
;
982 stream_forward_getp (s
, OSPF_DB_DESC_MIN_SIZE
);
983 for (size
-= OSPF_DB_DESC_MIN_SIZE
;
984 size
>= OSPF_LSA_HEADER_SIZE
; size
-= OSPF_LSA_HEADER_SIZE
)
986 lsah
= (struct lsa_header
*) STREAM_PNT (s
);
987 stream_forward_getp (s
, OSPF_LSA_HEADER_SIZE
);
989 /* Unknown LS type. */
990 if (lsah
->type
< OSPF_MIN_LSA
|| lsah
->type
>= OSPF_MAX_LSA
)
992 zlog_warn ("Packet [DD:RECV]: Unknown LS type %d.", lsah
->type
);
993 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
997 #ifdef HAVE_OPAQUE_LSA
998 if (IS_OPAQUE_LSA (lsah
->type
)
999 && ! CHECK_FLAG (nbr
->options
, OSPF_OPTION_O
))
1001 zlog_warn ("LSA[Type%d:%s]: Opaque capability mismatch?", lsah
->type
, inet_ntoa (lsah
->id
));
1002 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
1005 #endif /* HAVE_OPAQUE_LSA */
1009 case OSPF_AS_EXTERNAL_LSA
:
1010 #ifdef HAVE_OPAQUE_LSA
1011 case OSPF_OPAQUE_AS_LSA
:
1012 #endif /* HAVE_OPAQUE_LSA */
1013 /* Check for stub area. Reject if AS-External from stub but
1014 allow if from NSSA. */
1015 if (oi
->area
->external_routing
== OSPF_AREA_STUB
)
1017 zlog_warn ("Packet [DD:RECV]: LSA[Type%d:%s] from %s area.",
1018 lsah
->type
, inet_ntoa (lsah
->id
),
1019 (oi
->area
->external_routing
== OSPF_AREA_STUB
) ?\
1021 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
1029 /* Create LS-request object. */
1030 new = ospf_ls_request_new (lsah
);
1032 /* Lookup received LSA, then add LS request list. */
1033 find
= ospf_lsa_lookup_by_header (oi
->area
, lsah
);
1034 if (!find
|| ospf_lsa_more_recent (find
, new) < 0)
1036 ospf_ls_request_add (nbr
, new);
1037 ospf_lsa_discard (new);
1041 /* Received LSA is not recent. */
1042 if (IS_DEBUG_OSPF_EVENT
)
1043 zlog_debug ("Packet [DD:RECV]: LSA received Type %d, "
1044 "ID %s is not recent.", lsah
->type
, inet_ntoa (lsah
->id
));
1045 ospf_lsa_discard (new);
1051 if (IS_SET_DD_MS (nbr
->dd_flags
))
1054 /* Entire DD packet sent. */
1055 if (!IS_SET_DD_M (dd
->flags
) && !IS_SET_DD_M (nbr
->dd_flags
))
1056 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_ExchangeDone
);
1058 /* Send new DD packet. */
1059 ospf_db_desc_send (nbr
);
1064 nbr
->dd_seqnum
= ntohl (dd
->dd_seqnum
);
1066 /* When master's more flags is not set. */
1067 if (!IS_SET_DD_M (dd
->flags
) && ospf_db_summary_isempty (nbr
))
1069 nbr
->dd_flags
&= ~(OSPF_DD_FLAG_M
);
1070 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_ExchangeDone
);
1073 /* Send DD packet in reply. */
1074 ospf_db_desc_send (nbr
);
1077 /* Save received neighbor values from DD. */
1078 ospf_db_desc_save_current (nbr
, dd
);
1082 ospf_db_desc_is_dup (struct ospf_db_desc
*dd
, struct ospf_neighbor
*nbr
)
1084 /* Is DD duplicated? */
1085 if (dd
->options
== nbr
->last_recv
.options
&&
1086 dd
->flags
== nbr
->last_recv
.flags
&&
1087 dd
->dd_seqnum
== htonl (nbr
->last_recv
.dd_seqnum
))
1093 /* OSPF Database Description message read -- RFC2328 Section 10.6. */
1095 ospf_db_desc (struct ip
*iph
, struct ospf_header
*ospfh
,
1096 struct stream
*s
, struct ospf_interface
*oi
, u_int16_t size
)
1098 struct ospf_db_desc
*dd
;
1099 struct ospf_neighbor
*nbr
;
1101 /* Increment statistics. */
1104 dd
= (struct ospf_db_desc
*) STREAM_PNT (s
);
1106 nbr
= ospf_nbr_lookup (oi
, iph
, ospfh
);
1109 zlog_warn ("Packet[DD]: Unknown Neighbor %s",
1110 inet_ntoa (ospfh
->router_id
));
1115 if (ntohs (dd
->mtu
) > oi
->ifp
->mtu
)
1117 zlog_warn ("Packet[DD]: Neighbor %s MTU %u is larger than [%s]'s MTU %u",
1118 inet_ntoa (nbr
->router_id
), ntohs (dd
->mtu
),
1119 IF_NAME (oi
), oi
->ifp
->mtu
);
1124 * XXX HACK by Hasso Tepper. Setting N/P bit in NSSA area DD packets is not
1125 * required. In fact at least JunOS sends DD packets with P bit clear.
1126 * Until proper solution is developped, this hack should help.
1128 * Update: According to the RFCs, N bit is specified /only/ for Hello
1129 * options, unfortunately its use in DD options is not specified. Hence some
1130 * implementations follow E-bit semantics and set it in DD options, and some
1131 * treat it as unspecified and hence follow the directive "default for
1132 * options is clear", ie unset.
1134 * Reset the flag, as ospfd follows E-bit semantics.
1136 if ( (oi
->area
->external_routing
== OSPF_AREA_NSSA
)
1137 && (CHECK_FLAG (nbr
->options
, OSPF_OPTION_NP
))
1138 && (!CHECK_FLAG (dd
->options
, OSPF_OPTION_NP
)) )
1140 if (IS_DEBUG_OSPF_EVENT
)
1141 zlog_debug ("Packet[DD]: Neighbour %s: Has NSSA capability, sends with N bit clear in DD options",
1142 inet_ntoa (nbr
->router_id
) );
1143 SET_FLAG (dd
->options
, OSPF_OPTION_NP
);
1146 #ifdef REJECT_IF_TBIT_ON
1147 if (CHECK_FLAG (dd
->options
, OSPF_OPTION_T
))
1150 * In Hello protocol, optional capability must have checked
1151 * to prevent this T-bit enabled router be my neighbor.
1153 zlog_warn ("Packet[DD]: Neighbor %s: T-bit on?", inet_ntoa (nbr
->router_id
));
1156 #endif /* REJECT_IF_TBIT_ON */
1158 #ifdef HAVE_OPAQUE_LSA
1159 if (CHECK_FLAG (dd
->options
, OSPF_OPTION_O
)
1160 && !CHECK_FLAG (oi
->ospf
->config
, OSPF_OPAQUE_CAPABLE
))
1163 * This node is not configured to handle O-bit, for now.
1164 * Clear it to ignore unsupported capability proposed by neighbor.
1166 UNSET_FLAG (dd
->options
, OSPF_OPTION_O
);
1168 #endif /* HAVE_OPAQUE_LSA */
1170 /* Process DD packet by neighbor status. */
1176 zlog_warn ("Packet[DD]: Neighbor %s state is %s, packet discarded.",
1177 inet_ntoa(nbr
->router_id
),
1178 LOOKUP (ospf_nsm_state_msg
, nbr
->state
));
1181 OSPF_NSM_EVENT_EXECUTE (nbr
, NSM_TwoWayReceived
);
1182 /* If the new state is ExStart, the processing of the current
1183 packet should then continue in this new state by falling
1184 through to case ExStart below. */
1185 if (nbr
->state
!= NSM_ExStart
)
1189 if ((IS_SET_DD_ALL (dd
->flags
) == OSPF_DD_FLAG_ALL
) &&
1190 (size
== OSPF_DB_DESC_MIN_SIZE
))
1192 if (IPV4_ADDR_CMP (&nbr
->router_id
, &oi
->ospf
->router_id
) > 0)
1194 /* We're Slave---obey */
1195 zlog_info ("Packet[DD]: Neighbor %s Negotiation done (Slave).",
1196 inet_ntoa(nbr
->router_id
));
1197 nbr
->dd_seqnum
= ntohl (dd
->dd_seqnum
);
1198 nbr
->dd_flags
&= ~(OSPF_DD_FLAG_MS
|OSPF_DD_FLAG_I
); /* Reset I/MS */
1202 /* We're Master, ignore the initial DBD from Slave */
1203 zlog_warn ("Packet[DD]: Neighbor %s: Initial DBD from Slave, "
1204 "ignoring.", inet_ntoa(nbr
->router_id
));
1208 /* Ack from the Slave */
1209 else if (!IS_SET_DD_MS (dd
->flags
) && !IS_SET_DD_I (dd
->flags
) &&
1210 ntohl (dd
->dd_seqnum
) == nbr
->dd_seqnum
&&
1211 IPV4_ADDR_CMP (&nbr
->router_id
, &oi
->ospf
->router_id
) < 0)
1213 zlog_info ("Packet[DD]: Neighbor %s Negotiation done (Master).",
1214 inet_ntoa(nbr
->router_id
));
1215 nbr
->dd_flags
&= ~OSPF_DD_FLAG_I
;
1219 zlog_warn ("Packet[DD]: Neighbor %s Negotiation fails.",
1220 inet_ntoa(nbr
->router_id
));
1224 /* This is where the real Options are saved */
1225 nbr
->options
= dd
->options
;
1227 #ifdef HAVE_OPAQUE_LSA
1228 if (CHECK_FLAG (oi
->ospf
->config
, OSPF_OPAQUE_CAPABLE
))
1230 if (IS_DEBUG_OSPF_EVENT
)
1231 zlog_debug ("Neighbor[%s] is %sOpaque-capable.",
1232 inet_ntoa (nbr
->router_id
),
1233 CHECK_FLAG (nbr
->options
, OSPF_OPTION_O
) ? "" : "NOT ");
1235 if (! CHECK_FLAG (nbr
->options
, OSPF_OPTION_O
)
1236 && IPV4_ADDR_SAME (&DR (oi
), &nbr
->address
.u
.prefix4
))
1238 zlog_warn ("DR-neighbor[%s] is NOT opaque-capable; Opaque-LSAs cannot be reliably advertised in this network.", inet_ntoa (nbr
->router_id
));
1239 /* This situation is undesirable, but not a real error. */
1242 #endif /* HAVE_OPAQUE_LSA */
1244 OSPF_NSM_EVENT_EXECUTE (nbr
, NSM_NegotiationDone
);
1246 /* continue processing rest of packet. */
1247 ospf_db_desc_proc (s
, oi
, nbr
, dd
, size
);
1250 if (ospf_db_desc_is_dup (dd
, nbr
))
1252 if (IS_SET_DD_MS (nbr
->dd_flags
))
1253 /* Master: discard duplicated DD packet. */
1254 zlog_warn ("Packet[DD] (Master): Neighbor %s packet duplicated.",
1255 inet_ntoa (nbr
->router_id
));
1257 /* Slave: cause to retransmit the last Database Description. */
1259 zlog_warn ("Packet[DD] [Slave]: Neighbor %s packet duplicated.",
1260 inet_ntoa (nbr
->router_id
));
1261 ospf_db_desc_resend (nbr
);
1266 /* Otherwise DD packet should be checked. */
1267 /* Check Master/Slave bit mismatch */
1268 if (IS_SET_DD_MS (dd
->flags
) != IS_SET_DD_MS (nbr
->last_recv
.flags
))
1270 zlog_warn ("Packet[DD]: Neighbor %s MS-bit mismatch.",
1271 inet_ntoa(nbr
->router_id
));
1272 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
1273 if (IS_DEBUG_OSPF_EVENT
)
1274 zlog_debug ("Packet[DD]: dd->flags=%d, nbr->dd_flags=%d",
1275 dd
->flags
, nbr
->dd_flags
);
1279 /* Check initialize bit is set. */
1280 if (IS_SET_DD_I (dd
->flags
))
1282 zlog_warn ("Packet[DD]: Neighbor %s I-bit set.",
1283 inet_ntoa(nbr
->router_id
));
1284 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
1288 /* Check DD Options. */
1289 if (dd
->options
!= nbr
->options
)
1291 #ifdef ORIGINAL_CODING
1292 /* Save the new options for debugging */
1293 nbr
->options
= dd
->options
;
1294 #endif /* ORIGINAL_CODING */
1295 zlog_warn ("Packet[DD]: Neighbor %s options mismatch.",
1296 inet_ntoa(nbr
->router_id
));
1297 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
1301 /* Check DD sequence number. */
1302 if ((IS_SET_DD_MS (nbr
->dd_flags
) &&
1303 ntohl (dd
->dd_seqnum
) != nbr
->dd_seqnum
) ||
1304 (!IS_SET_DD_MS (nbr
->dd_flags
) &&
1305 ntohl (dd
->dd_seqnum
) != nbr
->dd_seqnum
+ 1))
1307 zlog_warn ("Packet[DD]: Neighbor %s sequence number mismatch.",
1308 inet_ntoa(nbr
->router_id
));
1309 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
1313 /* Continue processing rest of packet. */
1314 ospf_db_desc_proc (s
, oi
, nbr
, dd
, size
);
1318 if (ospf_db_desc_is_dup (dd
, nbr
))
1320 if (IS_SET_DD_MS (nbr
->dd_flags
))
1322 /* Master should discard duplicate DD packet. */
1323 zlog_warn("Packet[DD]: Neighbor %s duplicated, packet discarded.",
1324 inet_ntoa(nbr
->router_id
));
1329 struct timeval t
, now
;
1330 gettimeofday (&now
, NULL
);
1331 t
= tv_sub (now
, nbr
->last_send_ts
);
1332 if (tv_cmp (t
, int2tv (nbr
->v_inactivity
)) < 0)
1334 /* In states Loading and Full the slave must resend
1335 its last Database Description packet in response to
1336 duplicate Database Description packets received
1337 from the master. For this reason the slave must
1338 wait RouterDeadInterval seconds before freeing the
1339 last Database Description packet. Reception of a
1340 Database Description packet from the master after
1341 this interval will generate a SeqNumberMismatch
1342 neighbor event. RFC2328 Section 10.8 */
1343 ospf_db_desc_resend (nbr
);
1349 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_SeqNumberMismatch
);
1352 zlog_warn ("Packet[DD]: Neighbor %s NSM illegal status %u.",
1353 inet_ntoa(nbr
->router_id
), nbr
->state
);
1358 #define OSPF_LSA_KEY_SIZE 12 /* type(4) + id(4) + ar(4) */
1360 /* OSPF Link State Request Read -- RFC2328 Section 10.7. */
1362 ospf_ls_req (struct ip
*iph
, struct ospf_header
*ospfh
,
1363 struct stream
*s
, struct ospf_interface
*oi
, u_int16_t size
)
1365 struct ospf_neighbor
*nbr
;
1367 struct in_addr ls_id
;
1368 struct in_addr adv_router
;
1369 struct ospf_lsa
*find
;
1370 struct list
*ls_upd
;
1371 unsigned int length
;
1373 /* Increment statistics. */
1376 nbr
= ospf_nbr_lookup (oi
, iph
, ospfh
);
1379 zlog_warn ("Link State Request: Unknown Neighbor %s.",
1380 inet_ntoa (ospfh
->router_id
));
1384 /* Neighbor State should be Exchange or later. */
1385 if (nbr
->state
!= NSM_Exchange
&&
1386 nbr
->state
!= NSM_Loading
&&
1387 nbr
->state
!= NSM_Full
)
1389 zlog_warn ("Link State Request received from %s: "
1390 "Neighbor state is %s, packet discarded.",
1391 inet_ntoa (ospfh
->router_id
),
1392 LOOKUP (ospf_nsm_state_msg
, nbr
->state
));
1396 /* Send Link State Update for ALL requested LSAs. */
1397 ls_upd
= list_new ();
1398 length
= OSPF_HEADER_SIZE
+ OSPF_LS_UPD_MIN_SIZE
;
1400 while (size
>= OSPF_LSA_KEY_SIZE
)
1402 /* Get one slice of Link State Request. */
1403 ls_type
= stream_getl (s
);
1404 ls_id
.s_addr
= stream_get_ipv4 (s
);
1405 adv_router
.s_addr
= stream_get_ipv4 (s
);
1407 /* Verify LSA type. */
1408 if (ls_type
< OSPF_MIN_LSA
|| ls_type
>= OSPF_MAX_LSA
)
1410 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_BadLSReq
);
1411 list_delete (ls_upd
);
1415 /* Search proper LSA in LSDB. */
1416 find
= ospf_lsa_lookup (oi
->area
, ls_type
, ls_id
, adv_router
);
1419 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_BadLSReq
);
1420 list_delete (ls_upd
);
1424 /* Packet overflows MTU size, send immediately. */
1425 if (length
+ ntohs (find
->data
->length
) > ospf_packet_max (oi
))
1427 if (oi
->type
== OSPF_IFTYPE_NBMA
)
1428 ospf_ls_upd_send (nbr
, ls_upd
, OSPF_SEND_PACKET_DIRECT
);
1430 ospf_ls_upd_send (nbr
, ls_upd
, OSPF_SEND_PACKET_INDIRECT
);
1432 /* Only remove list contents. Keep ls_upd. */
1433 list_delete_all_node (ls_upd
);
1435 length
= OSPF_HEADER_SIZE
+ OSPF_LS_UPD_MIN_SIZE
;
1438 /* Append LSA to update list. */
1439 listnode_add (ls_upd
, find
);
1440 length
+= ntohs (find
->data
->length
);
1442 size
-= OSPF_LSA_KEY_SIZE
;
1445 /* Send rest of Link State Update. */
1446 if (listcount (ls_upd
) > 0)
1448 if (oi
->type
== OSPF_IFTYPE_NBMA
)
1449 ospf_ls_upd_send (nbr
, ls_upd
, OSPF_SEND_PACKET_DIRECT
);
1451 ospf_ls_upd_send (nbr
, ls_upd
, OSPF_SEND_PACKET_INDIRECT
);
1453 list_delete (ls_upd
);
1459 /* Get the list of LSAs from Link State Update packet.
1460 And process some validation -- RFC2328 Section 13. (1)-(2). */
1461 static struct list
*
1462 ospf_ls_upd_list_lsa (struct ospf_neighbor
*nbr
, struct stream
*s
,
1463 struct ospf_interface
*oi
, size_t size
)
1465 u_int16_t count
, sum
;
1467 struct lsa_header
*lsah
;
1468 struct ospf_lsa
*lsa
;
1473 count
= stream_getl (s
);
1474 size
-= OSPF_LS_UPD_MIN_SIZE
; /* # LSAs */
1476 for (; size
>= OSPF_LSA_HEADER_SIZE
&& count
> 0;
1477 size
-= length
, stream_forward_getp (s
, length
), count
--)
1479 lsah
= (struct lsa_header
*) STREAM_PNT (s
);
1480 length
= ntohs (lsah
->length
);
1484 zlog_warn ("Link State Update: LSA length exceeds packet size.");
1488 /* Validate the LSA's LS checksum. */
1489 sum
= lsah
->checksum
;
1490 if (sum
!= ospf_lsa_checksum (lsah
))
1492 zlog_warn ("Link State Update: LSA checksum error %x, %x.",
1493 sum
, lsah
->checksum
);
1497 /* Examine the LSA's LS type. */
1498 if (lsah
->type
< OSPF_MIN_LSA
|| lsah
->type
>= OSPF_MAX_LSA
)
1500 zlog_warn ("Link State Update: Unknown LS type %d", lsah
->type
);
1505 * What if the received LSA's age is greater than MaxAge?
1506 * Treat it as a MaxAge case -- endo.
1508 if (ntohs (lsah
->ls_age
) > OSPF_LSA_MAXAGE
)
1509 lsah
->ls_age
= htons (OSPF_LSA_MAXAGE
);
1511 #ifdef HAVE_OPAQUE_LSA
1512 if (CHECK_FLAG (nbr
->options
, OSPF_OPTION_O
))
1514 #ifdef STRICT_OBIT_USAGE_CHECK
1515 if ((IS_OPAQUE_LSA(lsah
->type
) &&
1516 ! CHECK_FLAG (lsah
->options
, OSPF_OPTION_O
))
1517 || (! IS_OPAQUE_LSA(lsah
->type
) &&
1518 CHECK_FLAG (lsah
->options
, OSPF_OPTION_O
)))
1521 * This neighbor must know the exact usage of O-bit;
1522 * the bit will be set in Type-9,10,11 LSAs only.
1524 zlog_warn ("LSA[Type%d:%s]: O-bit abuse?", lsah
->type
, inet_ntoa (lsah
->id
));
1527 #endif /* STRICT_OBIT_USAGE_CHECK */
1529 /* Do not take in AS External Opaque-LSAs if we are a stub. */
1530 if (lsah
->type
== OSPF_OPAQUE_AS_LSA
1531 && nbr
->oi
->area
->external_routing
!= OSPF_AREA_DEFAULT
)
1533 if (IS_DEBUG_OSPF_EVENT
)
1534 zlog_debug ("LSA[Type%d:%s]: We are a stub, don't take this LSA.", lsah
->type
, inet_ntoa (lsah
->id
));
1538 else if (IS_OPAQUE_LSA(lsah
->type
))
1540 zlog_warn ("LSA[Type%d:%s]: Opaque capability mismatch?", lsah
->type
, inet_ntoa (lsah
->id
));
1543 #endif /* HAVE_OPAQUE_LSA */
1545 /* Create OSPF LSA instance. */
1546 lsa
= ospf_lsa_new ();
1548 /* We may wish to put some error checking if type NSSA comes in
1549 and area not in NSSA mode */
1552 case OSPF_AS_EXTERNAL_LSA
:
1553 #ifdef HAVE_OPAQUE_LSA
1554 case OSPF_OPAQUE_AS_LSA
:
1557 case OSPF_OPAQUE_LINK_LSA
:
1558 lsa
->oi
= oi
; /* Remember incoming interface for flooding control. */
1560 #endif /* HAVE_OPAQUE_LSA */
1562 lsa
->area
= oi
->area
;
1566 lsa
->data
= ospf_lsa_data_new (length
);
1567 memcpy (lsa
->data
, lsah
, length
);
1569 if (IS_DEBUG_OSPF_EVENT
)
1570 zlog_debug("LSA[Type%d:%s]: %p new LSA created with Link State Update",
1571 lsa
->data
->type
, inet_ntoa (lsa
->data
->id
), lsa
);
1572 listnode_add (lsas
, lsa
);
1578 /* Cleanup Update list. */
1580 ospf_upd_list_clean (struct list
*lsas
)
1582 struct listnode
*node
, *nnode
;
1583 struct ospf_lsa
*lsa
;
1585 for (ALL_LIST_ELEMENTS (lsas
, node
, nnode
, lsa
))
1586 ospf_lsa_discard (lsa
);
1591 /* OSPF Link State Update message read -- RFC2328 Section 13. */
1593 ospf_ls_upd (struct ip
*iph
, struct ospf_header
*ospfh
,
1594 struct stream
*s
, struct ospf_interface
*oi
, u_int16_t size
)
1596 struct ospf_neighbor
*nbr
;
1598 #ifdef HAVE_OPAQUE_LSA
1599 struct list
*mylsa_acks
, *mylsa_upds
;
1600 #endif /* HAVE_OPAQUE_LSA */
1601 struct listnode
*node
, *nnode
;
1602 struct ospf_lsa
*lsa
= NULL
;
1603 /* unsigned long ls_req_found = 0; */
1605 /* Dis-assemble the stream, update each entry, re-encapsulate for flooding */
1607 /* Increment statistics. */
1610 /* Check neighbor. */
1611 nbr
= ospf_nbr_lookup (oi
, iph
, ospfh
);
1614 zlog_warn ("Link State Update: Unknown Neighbor %s on int: %s",
1615 inet_ntoa (ospfh
->router_id
), IF_NAME (oi
));
1619 /* Check neighbor state. */
1620 if (nbr
->state
< NSM_Exchange
)
1622 zlog_warn ("Link State Update: "
1623 "Neighbor[%s] state %s is less than Exchange",
1624 inet_ntoa (ospfh
->router_id
),
1625 LOOKUP(ospf_nsm_state_msg
, nbr
->state
));
1629 /* Get list of LSAs from Link State Update packet. - Also perorms Stages
1630 * 1 (validate LSA checksum) and 2 (check for LSA consistent type)
1633 lsas
= ospf_ls_upd_list_lsa (nbr
, s
, oi
, size
);
1635 #ifdef HAVE_OPAQUE_LSA
1637 * Prepare two kinds of lists to clean up unwanted self-originated
1638 * Opaque-LSAs from the routing domain as soon as possible.
1640 mylsa_acks
= list_new (); /* Let the sender cease retransmission. */
1641 mylsa_upds
= list_new (); /* Flush target LSAs if necessary. */
1644 * If self-originated Opaque-LSAs that have flooded before restart
1645 * are contained in the received LSUpd message, corresponding LSReq
1646 * messages to be sent may have to be modified.
1647 * To eliminate possible race conditions such that flushing and normal
1648 * updating for the same LSA would take place alternately, this trick
1649 * must be done before entering to the loop below.
1651 ospf_opaque_adjust_lsreq (nbr
, lsas
);
1652 #endif /* HAVE_OPAQUE_LSA */
1654 #define DISCARD_LSA(L,N) {\
1655 if (IS_DEBUG_OSPF_EVENT) \
1656 zlog_debug ("ospf_lsa_discard() in ospf_ls_upd() point %d: lsa %p Type-%d", N, lsa, (int) lsa->data->type); \
1657 ospf_lsa_discard (L); \
1660 /* Process each LSA received in the one packet. */
1661 for (ALL_LIST_ELEMENTS (lsas
, node
, nnode
, lsa
))
1663 struct ospf_lsa
*ls_ret
, *current
;
1666 if (IS_DEBUG_OSPF_NSSA
)
1668 char buf1
[INET_ADDRSTRLEN
];
1669 char buf2
[INET_ADDRSTRLEN
];
1670 char buf3
[INET_ADDRSTRLEN
];
1672 zlog_debug("LSA Type-%d from %s, ID: %s, ADV: %s",
1674 inet_ntop (AF_INET
, &ospfh
->router_id
,
1675 buf1
, INET_ADDRSTRLEN
),
1676 inet_ntop (AF_INET
, &lsa
->data
->id
,
1677 buf2
, INET_ADDRSTRLEN
),
1678 inet_ntop (AF_INET
, &lsa
->data
->adv_router
,
1679 buf3
, INET_ADDRSTRLEN
));
1682 listnode_delete (lsas
, lsa
); /* We don't need it in list anymore */
1684 /* Validate Checksum - Done above by ospf_ls_upd_list_lsa() */
1686 /* LSA Type - Done above by ospf_ls_upd_list_lsa() */
1688 /* Do not take in AS External LSAs if we are a stub or NSSA. */
1690 /* Do not take in AS NSSA if this neighbor and we are not NSSA */
1692 /* Do take in Type-7's if we are an NSSA */
1694 /* If we are also an ABR, later translate them to a Type-5 packet */
1696 /* Later, an NSSA Re-fresh can Re-fresh Type-7's and an ABR will
1697 translate them to a separate Type-5 packet. */
1699 if (lsa
->data
->type
== OSPF_AS_EXTERNAL_LSA
)
1700 /* Reject from STUB or NSSA */
1701 if (nbr
->oi
->area
->external_routing
!= OSPF_AREA_DEFAULT
)
1703 DISCARD_LSA (lsa
, 1);
1704 if (IS_DEBUG_OSPF_NSSA
)
1705 zlog_debug("Incoming External LSA Discarded: We are NSSA/STUB Area");
1708 if (lsa
->data
->type
== OSPF_AS_NSSA_LSA
)
1709 if (nbr
->oi
->area
->external_routing
!= OSPF_AREA_NSSA
)
1711 DISCARD_LSA (lsa
,2);
1712 if (IS_DEBUG_OSPF_NSSA
)
1713 zlog_debug("Incoming NSSA LSA Discarded: Not NSSA Area");
1716 /* Find the LSA in the current database. */
1718 current
= ospf_lsa_lookup_by_header (oi
->area
, lsa
->data
);
1720 /* If the LSA's LS age is equal to MaxAge, and there is currently
1721 no instance of the LSA in the router's link state database,
1722 and none of router's neighbors are in states Exchange or Loading,
1723 then take the following actions. */
1725 if (IS_LSA_MAXAGE (lsa
) && !current
&&
1726 (ospf_nbr_count (oi
, NSM_Exchange
) +
1727 ospf_nbr_count (oi
, NSM_Loading
)) == 0)
1729 /* Response Link State Acknowledgment. */
1730 ospf_ls_ack_send (nbr
, lsa
);
1733 zlog_warn("Link State Update[%s]: LS age is equal to MaxAge.",
1735 DISCARD_LSA (lsa
, 3);
1738 #ifdef HAVE_OPAQUE_LSA
1739 if (IS_OPAQUE_LSA (lsa
->data
->type
)
1740 && IPV4_ADDR_SAME (&lsa
->data
->adv_router
, &oi
->ospf
->router_id
))
1743 * Even if initial flushing seems to be completed, there might
1744 * be a case that self-originated LSA with MaxAge still remain
1745 * in the routing domain.
1746 * Just send an LSAck message to cease retransmission.
1748 if (IS_LSA_MAXAGE (lsa
))
1750 zlog_warn ("LSA[%s]: Boomerang effect?", dump_lsa_key (lsa
));
1751 ospf_ls_ack_send (nbr
, lsa
);
1752 ospf_lsa_discard (lsa
);
1754 if (current
!= NULL
&& ! IS_LSA_MAXAGE (current
))
1755 ospf_opaque_lsa_refresh_schedule (current
);
1760 * If an instance of self-originated Opaque-LSA is not found
1761 * in the LSDB, there are some possible cases here.
1763 * 1) This node lost opaque-capability after restart.
1764 * 2) Else, a part of opaque-type is no more supported.
1765 * 3) Else, a part of opaque-id is no more supported.
1767 * Anyway, it is still this node's responsibility to flush it.
1768 * Otherwise, the LSA instance remains in the routing domain
1769 * until its age reaches to MaxAge.
1771 if (current
== NULL
)
1773 if (IS_DEBUG_OSPF_EVENT
)
1774 zlog_debug ("LSA[%s]: Previously originated Opaque-LSA, not found in the LSDB.", dump_lsa_key (lsa
));
1776 SET_FLAG (lsa
->flags
, OSPF_LSA_SELF
);
1777 listnode_add (mylsa_upds
, ospf_lsa_dup (lsa
));
1778 listnode_add (mylsa_acks
, ospf_lsa_lock (lsa
));
1782 #endif /* HAVE_OPAQUE_LSA */
1783 /* It might be happen that received LSA is self-originated network LSA, but
1784 * router ID is cahnged. So, we should check if LSA is a network-LSA whose
1785 * Link State ID is one of the router's own IP interface addresses but whose
1786 * Advertising Router is not equal to the router's own Router ID
1787 * According to RFC 2328 12.4.2 and 13.4 this LSA should be flushed.
1790 if(lsa
->data
->type
== OSPF_NETWORK_LSA
)
1792 struct listnode
*oinode
, *oinnode
;
1793 struct ospf_interface
*out_if
;
1796 for (ALL_LIST_ELEMENTS (oi
->ospf
->oiflist
, oinode
, oinnode
, out_if
))
1801 if((IPV4_ADDR_SAME(&out_if
->address
->u
.prefix4
, &lsa
->data
->id
)) &&
1802 (!(IPV4_ADDR_SAME(&oi
->ospf
->router_id
, &lsa
->data
->adv_router
))))
1804 if(out_if
->network_lsa_self
)
1806 ospf_lsa_flush_area(lsa
,out_if
->area
);
1807 if(IS_DEBUG_OSPF_EVENT
)
1808 zlog_debug ("ospf_lsa_discard() in ospf_ls_upd() point 9: lsa %p Type-%d",
1809 lsa
, (int) lsa
->data
->type
);
1810 ospf_lsa_discard (lsa
);
1820 /* (5) Find the instance of this LSA that is currently contained
1821 in the router's link state database. If there is no
1822 database copy, or the received LSA is more recent than
1823 the database copy the following steps must be performed. */
1825 if (current
== NULL
||
1826 (ret
= ospf_lsa_more_recent (current
, lsa
)) < 0)
1828 /* Actual flooding procedure. */
1829 if (ospf_flood (oi
->ospf
, nbr
, current
, lsa
) < 0) /* Trap NSSA later. */
1830 DISCARD_LSA (lsa
, 4);
1834 /* (6) Else, If there is an instance of the LSA on the sending
1835 neighbor's Link state request list, an error has occurred in
1836 the Database Exchange process. In this case, restart the
1837 Database Exchange process by generating the neighbor event
1838 BadLSReq for the sending neighbor and stop processing the
1839 Link State Update packet. */
1841 if (ospf_ls_request_lookup (nbr
, lsa
))
1843 OSPF_NSM_EVENT_SCHEDULE (nbr
, NSM_BadLSReq
);
1844 zlog_warn("LSA[%s] instance exists on Link state request list",
1847 /* Clean list of LSAs. */
1848 ospf_upd_list_clean (lsas
);
1849 /* this lsa is not on lsas list already. */
1850 ospf_lsa_discard (lsa
);
1851 #ifdef HAVE_OPAQUE_LSA
1852 list_delete (mylsa_acks
);
1853 list_delete (mylsa_upds
);
1854 #endif /* HAVE_OPAQUE_LSA */
1858 /* If the received LSA is the same instance as the database copy
1859 (i.e., neither one is more recent) the following two steps
1860 should be performed: */
1864 /* If the LSA is listed in the Link state retransmission list
1865 for the receiving adjacency, the router itself is expecting
1866 an acknowledgment for this LSA. The router should treat the
1867 received LSA as an acknowledgment by removing the LSA from
1868 the Link state retransmission list. This is termed an
1869 "implied acknowledgment". */
1871 ls_ret
= ospf_ls_retransmit_lookup (nbr
, lsa
);
1875 ospf_ls_retransmit_delete (nbr
, ls_ret
);
1877 /* Delayed acknowledgment sent if advertisement received
1878 from Designated Router, otherwise do nothing. */
1879 if (oi
->state
== ISM_Backup
)
1880 if (NBR_IS_DR (nbr
))
1881 listnode_add (oi
->ls_ack
, ospf_lsa_lock (lsa
));
1883 DISCARD_LSA (lsa
, 5);
1886 /* Acknowledge the receipt of the LSA by sending a
1887 Link State Acknowledgment packet back out the receiving
1890 ospf_ls_ack_send (nbr
, lsa
);
1891 DISCARD_LSA (lsa
, 6);
1895 /* The database copy is more recent. If the database copy
1896 has LS age equal to MaxAge and LS sequence number equal to
1897 MaxSequenceNumber, simply discard the received LSA without
1898 acknowledging it. (In this case, the LSA's LS sequence number is
1899 wrapping, and the MaxSequenceNumber LSA must be completely
1900 flushed before any new LSA instance can be introduced). */
1902 else if (ret
> 0) /* Database copy is more recent */
1904 if (IS_LSA_MAXAGE (current
) &&
1905 current
->data
->ls_seqnum
== htonl (OSPF_MAX_SEQUENCE_NUMBER
))
1907 DISCARD_LSA (lsa
, 7);
1909 /* Otherwise, as long as the database copy has not been sent in a
1910 Link State Update within the last MinLSArrival seconds, send the
1911 database copy back to the sending neighbor, encapsulated within
1912 a Link State Update Packet. The Link State Update Packet should
1913 be sent directly to the neighbor. In so doing, do not put the
1914 database copy of the LSA on the neighbor's link state
1915 retransmission list, and do not acknowledge the received (less
1916 recent) LSA instance. */
1921 gettimeofday (&now
, NULL
);
1923 if (tv_cmp (tv_sub (now
, current
->tv_orig
),
1924 int2tv (OSPF_MIN_LS_ARRIVAL
)) > 0)
1925 /* Trap NSSA type later.*/
1926 ospf_ls_upd_send_lsa (nbr
, current
, OSPF_SEND_PACKET_DIRECT
);
1927 DISCARD_LSA (lsa
, 8);
1932 #ifdef HAVE_OPAQUE_LSA
1934 * Now that previously originated Opaque-LSAs those which not yet
1935 * installed into LSDB are captured, take several steps to clear
1936 * them completely from the routing domain, before proceeding to
1937 * origination for the current target Opaque-LSAs.
1939 while (listcount (mylsa_acks
) > 0)
1940 ospf_ls_ack_send_list (oi
, mylsa_acks
, nbr
->address
.u
.prefix4
);
1942 if (listcount (mylsa_upds
) > 0)
1943 ospf_opaque_self_originated_lsa_received (nbr
, mylsa_upds
);
1945 list_delete (mylsa_upds
);
1946 list_delete (mylsa_acks
);
1947 #endif /* HAVE_OPAQUE_LSA */
1949 assert (listcount (lsas
) == 0);
1953 /* OSPF Link State Acknowledgment message read -- RFC2328 Section 13.7. */
1955 ospf_ls_ack (struct ip
*iph
, struct ospf_header
*ospfh
,
1956 struct stream
*s
, struct ospf_interface
*oi
, u_int16_t size
)
1958 struct ospf_neighbor
*nbr
;
1959 #ifdef HAVE_OPAQUE_LSA
1960 struct list
*opaque_acks
;
1961 #endif /* HAVE_OPAQUE_LSA */
1963 /* increment statistics. */
1966 nbr
= ospf_nbr_lookup (oi
, iph
, ospfh
);
1969 zlog_warn ("Link State Acknowledgment: Unknown Neighbor %s.",
1970 inet_ntoa (ospfh
->router_id
));
1974 if (nbr
->state
< NSM_Exchange
)
1976 zlog_warn ("Link State Acknowledgment: "
1977 "Neighbor[%s] state %s is less than Exchange",
1978 inet_ntoa (ospfh
->router_id
),
1979 LOOKUP(ospf_nsm_state_msg
, nbr
->state
));
1983 #ifdef HAVE_OPAQUE_LSA
1984 opaque_acks
= list_new ();
1985 #endif /* HAVE_OPAQUE_LSA */
1987 while (size
>= OSPF_LSA_HEADER_SIZE
)
1989 struct ospf_lsa
*lsa
, *lsr
;
1991 lsa
= ospf_lsa_new ();
1992 lsa
->data
= (struct lsa_header
*) STREAM_PNT (s
);
1994 /* lsah = (struct lsa_header *) STREAM_PNT (s); */
1995 size
-= OSPF_LSA_HEADER_SIZE
;
1996 stream_forward_getp (s
, OSPF_LSA_HEADER_SIZE
);
1998 if (lsa
->data
->type
< OSPF_MIN_LSA
|| lsa
->data
->type
>= OSPF_MAX_LSA
)
2001 ospf_lsa_discard (lsa
);
2005 lsr
= ospf_ls_retransmit_lookup (nbr
, lsa
);
2007 if (lsr
!= NULL
&& lsr
->data
->ls_seqnum
== lsa
->data
->ls_seqnum
)
2009 #ifdef HAVE_OPAQUE_LSA
2010 /* Keep this LSA entry for later reference. */
2011 if (IS_OPAQUE_LSA (lsr
->data
->type
))
2012 listnode_add (opaque_acks
, ospf_lsa_dup (lsr
));
2013 #endif /* HAVE_OPAQUE_LSA */
2015 ospf_ls_retransmit_delete (nbr
, lsr
);
2019 ospf_lsa_discard (lsa
);
2022 #ifdef HAVE_OPAQUE_LSA
2023 if (listcount (opaque_acks
) > 0)
2024 ospf_opaque_ls_ack_received (nbr
, opaque_acks
);
2026 list_delete (opaque_acks
);
2028 #endif /* HAVE_OPAQUE_LSA */
2031 static struct stream
*
2032 ospf_recv_packet (int fd
, struct interface
**ifp
, struct stream
*ibuf
)
2037 unsigned int ifindex
= 0;
2039 /* Header and data both require alignment. */
2040 char buff
[CMSG_SPACE(SOPT_SIZE_CMSG_IFINDEX_IPV4())];
2043 memset (&msgh
, 0, sizeof (struct msghdr
));
2044 msgh
.msg_iov
= &iov
;
2045 msgh
.msg_iovlen
= 1;
2046 msgh
.msg_control
= (caddr_t
) buff
;
2047 msgh
.msg_controllen
= sizeof (buff
);
2049 ret
= stream_recvmsg (ibuf
, fd
, &msgh
, 0, OSPF_MAX_PACKET_SIZE
+1);
2052 zlog_warn("stream_recvmsg failed: %s", safe_strerror(errno
));
2055 if (ret
< sizeof(iph
))
2057 zlog_warn("ospf_recv_packet: discarding runt packet of length %d "
2058 "(ip header size is %u)",
2059 ret
, (u_int
)sizeof(iph
));
2063 /* Note that there should not be alignment problems with this assignment
2064 because this is at the beginning of the stream data buffer. */
2065 iph
= (struct ip
*) STREAM_DATA(ibuf
);
2066 sockopt_iphdrincl_swab_systoh (iph
);
2068 ip_len
= iph
->ip_len
;
2070 #if !defined(GNU_LINUX) && (OpenBSD < 200311)
2072 * Kernel network code touches incoming IP header parameters,
2073 * before protocol specific processing.
2075 * 1) Convert byteorder to host representation.
2076 * --> ip_len, ip_id, ip_off
2078 * 2) Adjust ip_len to strip IP header size!
2079 * --> If user process receives entire IP packet via RAW
2080 * socket, it must consider adding IP header size to
2081 * the "ip_len" field of "ip" structure.
2083 * For more details, see <netinet/ip_input.c>.
2085 ip_len
= ip_len
+ (iph
->ip_hl
<< 2);
2088 ifindex
= getsockopt_ifindex (AF_INET
, &msgh
);
2090 *ifp
= if_lookup_by_index (ifindex
);
2094 zlog_warn ("ospf_recv_packet read length mismatch: ip_len is %d, "
2095 "but recvmsg returned %d", ip_len
, ret
);
2102 struct ospf_interface
*
2103 ospf_associate_packet_vl (struct ospf
*ospf
, struct interface
*ifp
,
2104 struct ip
*iph
, struct ospf_header
*ospfh
)
2106 struct ospf_interface
*rcv_oi
;
2107 struct ospf_vl_data
*vl_data
;
2108 struct ospf_area
*vl_area
;
2109 struct listnode
*node
;
2111 if (IN_MULTICAST (ntohl (iph
->ip_dst
.s_addr
)) ||
2112 !OSPF_IS_AREA_BACKBONE (ospfh
))
2115 /* look for local OSPF interface matching the destination
2116 * to determine Area ID. We presume therefore the destination address
2117 * is unique, or at least (for "unnumbered" links), not used in other
2120 if ((rcv_oi
= ospf_if_lookup_by_local_addr (ospf
, NULL
,
2121 iph
->ip_dst
)) == NULL
)
2124 for (ALL_LIST_ELEMENTS_RO (ospf
->vlinks
, node
, vl_data
))
2126 vl_area
= ospf_area_lookup_by_area_id (ospf
, vl_data
->vl_area_id
);
2130 if (OSPF_AREA_SAME (&vl_area
, &rcv_oi
->area
) &&
2131 IPV4_ADDR_SAME (&vl_data
->vl_peer
, &ospfh
->router_id
))
2133 if (IS_DEBUG_OSPF_EVENT
)
2134 zlog_debug ("associating packet with %s",
2135 IF_NAME (vl_data
->vl_oi
));
2136 if (! CHECK_FLAG (vl_data
->vl_oi
->ifp
->flags
, IFF_UP
))
2138 if (IS_DEBUG_OSPF_EVENT
)
2139 zlog_debug ("This VL is not up yet, sorry");
2143 return vl_data
->vl_oi
;
2147 if (IS_DEBUG_OSPF_EVENT
)
2148 zlog_debug ("couldn't find any VL to associate the packet with");
2154 ospf_check_area_id (struct ospf_interface
*oi
, struct ospf_header
*ospfh
)
2156 /* Check match the Area ID of the receiving interface. */
2157 if (OSPF_AREA_SAME (&oi
->area
, &ospfh
))
2163 /* Unbound socket will accept any Raw IP packets if proto is matched.
2164 To prevent it, compare src IP address and i/f address with masking
2165 i/f network mask. */
2167 ospf_check_network_mask (struct ospf_interface
*oi
, struct in_addr ip_src
)
2169 struct in_addr mask
, me
, him
;
2171 if (oi
->type
== OSPF_IFTYPE_POINTOPOINT
||
2172 oi
->type
== OSPF_IFTYPE_VIRTUALLINK
)
2175 masklen2ip (oi
->address
->prefixlen
, &mask
);
2177 me
.s_addr
= oi
->address
->u
.prefix4
.s_addr
& mask
.s_addr
;
2178 him
.s_addr
= ip_src
.s_addr
& mask
.s_addr
;
2180 if (IPV4_ADDR_SAME (&me
, &him
))
2187 ospf_check_auth (struct ospf_interface
*oi
, struct stream
*ibuf
,
2188 struct ospf_header
*ospfh
)
2191 struct crypt_key
*ck
;
2193 switch (ntohs (ospfh
->auth_type
))
2195 case OSPF_AUTH_NULL
:
2198 case OSPF_AUTH_SIMPLE
:
2199 if (!memcmp (OSPF_IF_PARAM (oi
, auth_simple
), ospfh
->u
.auth_data
, OSPF_AUTH_SIMPLE_SIZE
))
2204 case OSPF_AUTH_CRYPTOGRAPHIC
:
2205 if ((ck
= listgetdata (listtail(OSPF_IF_PARAM (oi
,auth_crypt
)))) == NULL
)
2211 /* This is very basic, the digest processing is elsewhere */
2212 if (ospfh
->u
.crypt
.auth_data_len
== OSPF_AUTH_MD5_SIZE
&&
2213 ospfh
->u
.crypt
.key_id
== ck
->key_id
&&
2214 ntohs (ospfh
->length
) + OSPF_AUTH_SIMPLE_SIZE
<= stream_get_size (ibuf
))
2228 ospf_check_sum (struct ospf_header
*ospfh
)
2232 int in_cksum (void *ptr
, int nbytes
);
2234 /* clear auth_data for checksum. */
2235 memset (ospfh
->u
.auth_data
, 0, OSPF_AUTH_SIMPLE_SIZE
);
2237 /* keep checksum and clear. */
2238 sum
= ospfh
->checksum
;
2239 memset (&ospfh
->checksum
, 0, sizeof (u_int16_t
));
2241 /* calculate checksum. */
2242 ret
= in_cksum (ospfh
, ntohs (ospfh
->length
));
2246 zlog_info ("ospf_check_sum(): checksum mismatch, my %X, his %X",
2254 /* OSPF Header verification. */
2256 ospf_verify_header (struct stream
*ibuf
, struct ospf_interface
*oi
,
2257 struct ip
*iph
, struct ospf_header
*ospfh
)
2259 /* check version. */
2260 if (ospfh
->version
!= OSPF_VERSION
)
2262 zlog_warn ("interface %s: ospf_read version number mismatch.",
2267 /* Check Area ID. */
2268 if (!ospf_check_area_id (oi
, ospfh
))
2270 zlog_warn ("interface %s: ospf_read invalid Area ID %s.",
2271 IF_NAME (oi
), inet_ntoa (ospfh
->area_id
));
2275 /* Check network mask, Silently discarded. */
2276 if (! ospf_check_network_mask (oi
, iph
->ip_src
))
2278 zlog_warn ("interface %s: ospf_read network address is not same [%s]",
2279 IF_NAME (oi
), inet_ntoa (iph
->ip_src
));
2283 /* Check authentication. */
2284 if (ospf_auth_type (oi
) != ntohs (ospfh
->auth_type
))
2286 zlog_warn ("interface %s: ospf_read authentication type mismatch.",
2291 if (! ospf_check_auth (oi
, ibuf
, ospfh
))
2293 zlog_warn ("interface %s: ospf_read authentication failed.",
2298 /* if check sum is invalid, packet is discarded. */
2299 if (ntohs (ospfh
->auth_type
) != OSPF_AUTH_CRYPTOGRAPHIC
)
2301 if (! ospf_check_sum (ospfh
))
2303 zlog_warn ("interface %s: ospf_read packet checksum error %s",
2304 IF_NAME (oi
), inet_ntoa (ospfh
->router_id
));
2310 if (ospfh
->checksum
!= 0)
2312 if (ospf_check_md5_digest (oi
, ibuf
, ntohs (ospfh
->length
)) == 0)
2314 zlog_warn ("interface %s: ospf_read md5 authentication failed.",
2323 /* Starting point of packet process function. */
2325 ospf_read (struct thread
*thread
)
2328 struct stream
*ibuf
;
2330 struct ospf_interface
*oi
;
2332 struct ospf_header
*ospfh
;
2334 struct interface
*ifp
;
2336 /* first of all get interface pointer. */
2337 ospf
= THREAD_ARG (thread
);
2339 /* prepare for next packet. */
2340 ospf
->t_read
= thread_add_read (master
, ospf_read
, ospf
, ospf
->fd
);
2342 /* read OSPF packet. */
2343 stream_reset(ospf
->ibuf
);
2344 if (!(ibuf
= ospf_recv_packet (ospf
->fd
, &ifp
, ospf
->ibuf
)))
2347 /* Note that there should not be alignment problems with this assignment
2348 because this is at the beginning of the stream data buffer. */
2349 iph
= (struct ip
*) STREAM_DATA (ibuf
);
2350 /* Note that sockopt_iphdrincl_swab_systoh was called in ospf_recv_packet. */
2353 /* Handle cases where the platform does not support retrieving the ifindex,
2354 and also platforms (such as Solaris 8) that claim to support ifindex
2355 retrieval but do not. */
2356 ifp
= if_lookup_address (iph
->ip_src
);
2361 /* IP Header dump. */
2362 if (IS_DEBUG_OSPF_PACKET(0, RECV
))
2363 ospf_ip_header_dump (iph
);
2365 /* Self-originated packet should be discarded silently. */
2366 if (ospf_if_lookup_by_local_addr (ospf
, NULL
, iph
->ip_src
))
2368 if (IS_DEBUG_OSPF_PACKET (0, RECV
))
2370 zlog_debug ("ospf_read[%s]: Dropping self-originated packet",
2371 inet_ntoa (iph
->ip_src
));
2376 /* Adjust size to message length. */
2377 stream_forward_getp (ibuf
, iph
->ip_hl
* 4);
2379 /* Get ospf packet header. */
2380 ospfh
= (struct ospf_header
*) STREAM_PNT (ibuf
);
2382 /* associate packet with ospf interface */
2383 oi
= ospf_if_lookup_recv_if (ospf
, iph
->ip_src
);
2385 /* if no local ospf_interface,
2386 * or header area is backbone but ospf_interface is not
2387 * check for VLINK interface
2389 if ( (oi
== NULL
) ||
2390 (OSPF_IS_AREA_ID_BACKBONE(ospfh
->area_id
)
2391 && !OSPF_IS_AREA_ID_BACKBONE(oi
->area
->area_id
))
2394 if ((oi
= ospf_associate_packet_vl (ospf
, ifp
, iph
, ospfh
)) == NULL
)
2396 zlog_warn ("Packet from [%s] received on link %s"
2397 " but no ospf_interface",
2398 inet_ntoa (iph
->ip_src
), ifp
->name
);
2403 /* else it must be a local ospf interface, check it was received on
2406 else if (oi
->ifp
!= ifp
)
2408 zlog_warn ("Packet from [%s] received on wrong link %s",
2409 inet_ntoa (iph
->ip_src
), ifp
->name
);
2412 else if (oi
->state
== ISM_Down
)
2414 char buf
[2][INET_ADDRSTRLEN
];
2415 zlog_warn ("Ignoring packet from %s to %s received on interface that is "
2416 "down [%s]; interface flags are %s",
2417 inet_ntop(AF_INET
, &iph
->ip_src
, buf
[0], sizeof(buf
[0])),
2418 inet_ntop(AF_INET
, &iph
->ip_dst
, buf
[1], sizeof(buf
[1])),
2419 ifp
->name
, if_flag_dump(ifp
->flags
));
2420 /* Fix multicast memberships? */
2421 if (iph
->ip_dst
.s_addr
== htonl(OSPF_ALLSPFROUTERS
))
2422 SET_FLAG(oi
->multicast_memberships
, MEMBER_ALLROUTERS
);
2423 else if (iph
->ip_dst
.s_addr
== htonl(OSPF_ALLDROUTERS
))
2424 SET_FLAG(oi
->multicast_memberships
, MEMBER_DROUTERS
);
2425 if (oi
->multicast_memberships
)
2426 ospf_if_set_multicast(oi
);
2431 * If the received packet is destined for AllDRouters, the packet
2432 * should be accepted only if the received ospf interface state is
2433 * either DR or Backup -- endo.
2435 if (iph
->ip_dst
.s_addr
== htonl (OSPF_ALLDROUTERS
)
2436 && (oi
->state
!= ISM_DR
&& oi
->state
!= ISM_Backup
))
2438 zlog_warn ("Dropping packet for AllDRouters from [%s] via [%s] (ISM: %s)",
2439 inet_ntoa (iph
->ip_src
), IF_NAME (oi
),
2440 LOOKUP (ospf_ism_state_msg
, oi
->state
));
2441 /* Try to fix multicast membership. */
2442 SET_FLAG(oi
->multicast_memberships
, MEMBER_DROUTERS
);
2443 ospf_if_set_multicast(oi
);
2447 /* Show debug receiving packet. */
2448 if (IS_DEBUG_OSPF_PACKET (ospfh
->type
- 1, RECV
))
2450 if (IS_DEBUG_OSPF_PACKET (ospfh
->type
- 1, DETAIL
))
2452 zlog_debug ("-----------------------------------------------------");
2453 ospf_packet_dump (ibuf
);
2456 zlog_debug ("%s received from [%s] via [%s]",
2457 ospf_packet_type_str
[ospfh
->type
],
2458 inet_ntoa (ospfh
->router_id
), IF_NAME (oi
));
2459 zlog_debug (" src [%s],", inet_ntoa (iph
->ip_src
));
2460 zlog_debug (" dst [%s]", inet_ntoa (iph
->ip_dst
));
2462 if (IS_DEBUG_OSPF_PACKET (ospfh
->type
- 1, DETAIL
))
2463 zlog_debug ("-----------------------------------------------------");
2466 /* Some header verification. */
2467 ret
= ospf_verify_header (ibuf
, oi
, iph
, ospfh
);
2470 if (IS_DEBUG_OSPF_PACKET (ospfh
->type
- 1, RECV
))
2472 zlog_debug ("ospf_read[%s/%s]: Header check failed, "
2474 ospf_packet_type_str
[ospfh
->type
],
2475 inet_ntoa (iph
->ip_src
));
2480 stream_forward_getp (ibuf
, OSPF_HEADER_SIZE
);
2482 /* Adjust size to message length. */
2483 length
= ntohs (ospfh
->length
) - OSPF_HEADER_SIZE
;
2485 /* Read rest of the packet and call each sort of packet routine. */
2486 switch (ospfh
->type
)
2488 case OSPF_MSG_HELLO
:
2489 ospf_hello (iph
, ospfh
, ibuf
, oi
, length
);
2491 case OSPF_MSG_DB_DESC
:
2492 ospf_db_desc (iph
, ospfh
, ibuf
, oi
, length
);
2494 case OSPF_MSG_LS_REQ
:
2495 ospf_ls_req (iph
, ospfh
, ibuf
, oi
, length
);
2497 case OSPF_MSG_LS_UPD
:
2498 ospf_ls_upd (iph
, ospfh
, ibuf
, oi
, length
);
2500 case OSPF_MSG_LS_ACK
:
2501 ospf_ls_ack (iph
, ospfh
, ibuf
, oi
, length
);
2504 zlog (NULL
, LOG_WARNING
,
2505 "interface %s: OSPF packet header type %d is illegal",
2506 IF_NAME (oi
), ospfh
->type
);
2513 /* Make OSPF header. */
2515 ospf_make_header (int type
, struct ospf_interface
*oi
, struct stream
*s
)
2517 struct ospf_header
*ospfh
;
2519 ospfh
= (struct ospf_header
*) STREAM_DATA (s
);
2521 ospfh
->version
= (u_char
) OSPF_VERSION
;
2522 ospfh
->type
= (u_char
) type
;
2524 ospfh
->router_id
= oi
->ospf
->router_id
;
2526 ospfh
->checksum
= 0;
2527 ospfh
->area_id
= oi
->area
->area_id
;
2528 ospfh
->auth_type
= htons (ospf_auth_type (oi
));
2530 memset (ospfh
->u
.auth_data
, 0, OSPF_AUTH_SIMPLE_SIZE
);
2532 stream_forward_endp (s
, OSPF_HEADER_SIZE
);
2535 /* Make Authentication Data. */
2537 ospf_make_auth (struct ospf_interface
*oi
, struct ospf_header
*ospfh
)
2539 struct crypt_key
*ck
;
2541 switch (ospf_auth_type (oi
))
2543 case OSPF_AUTH_NULL
:
2544 /* memset (ospfh->u.auth_data, 0, sizeof (ospfh->u.auth_data)); */
2546 case OSPF_AUTH_SIMPLE
:
2547 memcpy (ospfh
->u
.auth_data
, OSPF_IF_PARAM (oi
, auth_simple
),
2548 OSPF_AUTH_SIMPLE_SIZE
);
2550 case OSPF_AUTH_CRYPTOGRAPHIC
:
2551 /* If key is not set, then set 0. */
2552 if (list_isempty (OSPF_IF_PARAM (oi
, auth_crypt
)))
2554 ospfh
->u
.crypt
.zero
= 0;
2555 ospfh
->u
.crypt
.key_id
= 0;
2556 ospfh
->u
.crypt
.auth_data_len
= OSPF_AUTH_MD5_SIZE
;
2560 ck
= listgetdata (listtail(OSPF_IF_PARAM (oi
, auth_crypt
)));
2561 ospfh
->u
.crypt
.zero
= 0;
2562 ospfh
->u
.crypt
.key_id
= ck
->key_id
;
2563 ospfh
->u
.crypt
.auth_data_len
= OSPF_AUTH_MD5_SIZE
;
2565 /* note: the seq is done in ospf_make_md5_digest() */
2568 /* memset (ospfh->u.auth_data, 0, sizeof (ospfh->u.auth_data)); */
2575 /* Fill rest of OSPF header. */
2577 ospf_fill_header (struct ospf_interface
*oi
,
2578 struct stream
*s
, u_int16_t length
)
2580 struct ospf_header
*ospfh
;
2582 ospfh
= (struct ospf_header
*) STREAM_DATA (s
);
2585 ospfh
->length
= htons (length
);
2587 /* Calculate checksum. */
2588 if (ntohs (ospfh
->auth_type
) != OSPF_AUTH_CRYPTOGRAPHIC
)
2589 ospfh
->checksum
= in_cksum (ospfh
, length
);
2591 ospfh
->checksum
= 0;
2593 /* Add Authentication Data. */
2594 ospf_make_auth (oi
, ospfh
);
2598 ospf_make_hello (struct ospf_interface
*oi
, struct stream
*s
)
2600 struct ospf_neighbor
*nbr
;
2601 struct route_node
*rn
;
2602 u_int16_t length
= OSPF_HELLO_MIN_SIZE
;
2603 struct in_addr mask
;
2607 /* Set netmask of interface. */
2608 if (oi
->type
!= OSPF_IFTYPE_POINTOPOINT
&&
2609 oi
->type
!= OSPF_IFTYPE_VIRTUALLINK
)
2610 masklen2ip (oi
->address
->prefixlen
, &mask
);
2612 memset ((char *) &mask
, 0, sizeof (struct in_addr
));
2613 stream_put_ipv4 (s
, mask
.s_addr
);
2615 /* Set Hello Interval. */
2616 stream_putw (s
, OSPF_IF_PARAM (oi
, v_hello
));
2618 if (IS_DEBUG_OSPF_EVENT
)
2619 zlog_debug ("make_hello: options: %x, int: %s",
2620 OPTIONS(oi
), IF_NAME (oi
));
2623 stream_putc (s
, OPTIONS (oi
));
2625 /* Set Router Priority. */
2626 stream_putc (s
, PRIORITY (oi
));
2628 /* Set Router Dead Interval. */
2629 stream_putl (s
, OSPF_IF_PARAM (oi
, v_wait
));
2631 /* Set Designated Router. */
2632 stream_put_ipv4 (s
, DR (oi
).s_addr
);
2634 p
= stream_get_endp (s
);
2636 /* Set Backup Designated Router. */
2637 stream_put_ipv4 (s
, BDR (oi
).s_addr
);
2639 /* Add neighbor seen. */
2640 for (rn
= route_top (oi
->nbrs
); rn
; rn
= route_next (rn
))
2641 if ((nbr
= rn
->info
))
2642 if (nbr
->router_id
.s_addr
!= 0) /* Ignore 0.0.0.0 node. */
2643 if (nbr
->state
!= NSM_Attempt
) /* Ignore Down neighbor. */
2644 if (nbr
->state
!= NSM_Down
) /* This is myself for DR election. */
2645 if (!IPV4_ADDR_SAME (&nbr
->router_id
, &oi
->ospf
->router_id
))
2647 /* Check neighbor is sane? */
2648 if (nbr
->d_router
.s_addr
!= 0
2649 && IPV4_ADDR_SAME (&nbr
->d_router
, &oi
->address
->u
.prefix4
)
2650 && IPV4_ADDR_SAME (&nbr
->bd_router
, &oi
->address
->u
.prefix4
))
2653 stream_put_ipv4 (s
, nbr
->router_id
.s_addr
);
2657 /* Let neighbor generate BackupSeen. */
2659 stream_putl_at (s
, p
, 0); /* ipv4 address, normally */
2665 ospf_make_db_desc (struct ospf_interface
*oi
, struct ospf_neighbor
*nbr
,
2668 struct ospf_lsa
*lsa
;
2669 u_int16_t length
= OSPF_DB_DESC_MIN_SIZE
;
2673 struct ospf_lsdb
*lsdb
;
2675 /* Set Interface MTU. */
2676 if (oi
->type
== OSPF_IFTYPE_VIRTUALLINK
)
2679 stream_putw (s
, oi
->ifp
->mtu
);
2682 options
= OPTIONS (oi
);
2683 #ifdef HAVE_OPAQUE_LSA
2684 if (CHECK_FLAG (oi
->ospf
->config
, OSPF_OPAQUE_CAPABLE
))
2686 if (IS_SET_DD_I (nbr
->dd_flags
)
2687 || CHECK_FLAG (nbr
->options
, OSPF_OPTION_O
))
2689 * Set O-bit in the outgoing DD packet for capablity negotiation,
2690 * if one of following case is applicable.
2692 * 1) WaitTimer expiration event triggered the neighbor state to
2693 * change to Exstart, but no (valid) DD packet has received
2694 * from the neighbor yet.
2696 * 2) At least one DD packet with O-bit on has received from the
2699 SET_FLAG (options
, OSPF_OPTION_O
);
2701 #endif /* HAVE_OPAQUE_LSA */
2702 stream_putc (s
, options
);
2704 /* Keep pointer to flags. */
2705 pp
= stream_get_endp (s
);
2706 stream_putc (s
, nbr
->dd_flags
);
2708 /* Set DD Sequence Number. */
2709 stream_putl (s
, nbr
->dd_seqnum
);
2711 if (ospf_db_summary_isempty (nbr
))
2713 if (nbr
->state
>= NSM_Exchange
)
2715 nbr
->dd_flags
&= ~OSPF_DD_FLAG_M
;
2716 /* Set DD flags again */
2717 stream_putc_at (s
, pp
, nbr
->dd_flags
);
2722 /* Describe LSA Header from Database Summary List. */
2723 lsdb
= &nbr
->db_sum
;
2725 for (i
= OSPF_MIN_LSA
; i
< OSPF_MAX_LSA
; i
++)
2727 struct route_table
*table
= lsdb
->type
[i
].db
;
2728 struct route_node
*rn
;
2730 for (rn
= route_top (table
); rn
; rn
= route_next (rn
))
2731 if ((lsa
= rn
->info
) != NULL
)
2733 #ifdef HAVE_OPAQUE_LSA
2734 if (IS_OPAQUE_LSA (lsa
->data
->type
)
2735 && (! CHECK_FLAG (options
, OSPF_OPTION_O
)))
2737 /* Suppress advertising opaque-informations. */
2738 /* Remove LSA from DB summary list. */
2739 ospf_lsdb_delete (lsdb
, lsa
);
2742 #endif /* HAVE_OPAQUE_LSA */
2744 if (!CHECK_FLAG (lsa
->flags
, OSPF_LSA_DISCARD
))
2746 struct lsa_header
*lsah
;
2749 /* DD packet overflows interface MTU. */
2750 if (length
+ OSPF_LSA_HEADER_SIZE
> ospf_packet_max (oi
))
2753 /* Keep pointer to LS age. */
2754 lsah
= (struct lsa_header
*) (STREAM_DATA (s
) +
2755 stream_get_endp (s
));
2757 /* Proceed stream pointer. */
2758 stream_put (s
, lsa
->data
, OSPF_LSA_HEADER_SIZE
);
2759 length
+= OSPF_LSA_HEADER_SIZE
;
2762 ls_age
= LS_AGE (lsa
);
2763 lsah
->ls_age
= htons (ls_age
);
2767 /* Remove LSA from DB summary list. */
2768 ospf_lsdb_delete (lsdb
, lsa
);
2776 ospf_make_ls_req_func (struct stream
*s
, u_int16_t
*length
,
2777 unsigned long delta
, struct ospf_neighbor
*nbr
,
2778 struct ospf_lsa
*lsa
)
2780 struct ospf_interface
*oi
;
2784 /* LS Request packet overflows interface MTU. */
2785 if (*length
+ delta
> ospf_packet_max(oi
))
2788 stream_putl (s
, lsa
->data
->type
);
2789 stream_put_ipv4 (s
, lsa
->data
->id
.s_addr
);
2790 stream_put_ipv4 (s
, lsa
->data
->adv_router
.s_addr
);
2792 ospf_lsa_unlock (nbr
->ls_req_last
);
2793 nbr
->ls_req_last
= ospf_lsa_lock (lsa
);
2800 ospf_make_ls_req (struct ospf_neighbor
*nbr
, struct stream
*s
)
2802 struct ospf_lsa
*lsa
;
2803 u_int16_t length
= OSPF_LS_REQ_MIN_SIZE
;
2804 unsigned long delta
= stream_get_endp(s
)+12;
2805 struct route_table
*table
;
2806 struct route_node
*rn
;
2808 struct ospf_lsdb
*lsdb
;
2810 lsdb
= &nbr
->ls_req
;
2812 for (i
= OSPF_MIN_LSA
; i
< OSPF_MAX_LSA
; i
++)
2814 table
= lsdb
->type
[i
].db
;
2815 for (rn
= route_top (table
); rn
; rn
= route_next (rn
))
2816 if ((lsa
= (rn
->info
)) != NULL
)
2817 if (ospf_make_ls_req_func (s
, &length
, delta
, nbr
, lsa
) == 0)
2819 route_unlock_node (rn
);
2827 ls_age_increment (struct ospf_lsa
*lsa
, int delay
)
2831 age
= IS_LSA_MAXAGE (lsa
) ? OSPF_LSA_MAXAGE
: LS_AGE (lsa
) + delay
;
2833 return (age
> OSPF_LSA_MAXAGE
? OSPF_LSA_MAXAGE
: age
);
2837 ospf_make_ls_upd (struct ospf_interface
*oi
, struct list
*update
, struct stream
*s
)
2839 struct ospf_lsa
*lsa
;
2840 struct listnode
*node
;
2841 u_int16_t length
= OSPF_LS_UPD_MIN_SIZE
;
2842 unsigned int size_noauth
;
2843 unsigned long delta
= stream_get_endp (s
);
2847 if (IS_DEBUG_OSPF_EVENT
)
2848 zlog_debug ("ospf_make_ls_upd: Start");
2850 pp
= stream_get_endp (s
);
2851 stream_forward_endp (s
, OSPF_LS_UPD_MIN_SIZE
);
2853 /* Calculate amount of packet usable for data. */
2854 size_noauth
= stream_get_size(s
) - ospf_packet_authspace(oi
);
2856 while ((node
= listhead (update
)) != NULL
)
2858 struct lsa_header
*lsah
;
2861 if (IS_DEBUG_OSPF_EVENT
)
2862 zlog_debug ("ospf_make_ls_upd: List Iteration");
2864 lsa
= listgetdata (node
);
2869 if (length
+ delta
+ ntohs (lsa
->data
->length
) > size_noauth
)
2872 /* Keep pointer to LS age. */
2873 lsah
= (struct lsa_header
*) (STREAM_DATA (s
) + stream_get_endp (s
));
2875 /* Put LSA to Link State Request. */
2876 stream_put (s
, lsa
->data
, ntohs (lsa
->data
->length
));
2879 /* each hop must increment an lsa_age by transmit_delay
2880 of OSPF interface */
2881 ls_age
= ls_age_increment (lsa
, OSPF_IF_PARAM (oi
, transmit_delay
));
2882 lsah
->ls_age
= htons (ls_age
);
2884 length
+= ntohs (lsa
->data
->length
);
2887 list_delete_node (update
, node
);
2888 ospf_lsa_unlock (lsa
);
2891 /* Now set #LSAs. */
2892 stream_putl_at (s
, pp
, count
);
2894 if (IS_DEBUG_OSPF_EVENT
)
2895 zlog_debug ("ospf_make_ls_upd: Stop");
2900 ospf_make_ls_ack (struct ospf_interface
*oi
, struct list
*ack
, struct stream
*s
)
2902 struct list
*rm_list
;
2903 struct listnode
*node
;
2904 u_int16_t length
= OSPF_LS_ACK_MIN_SIZE
;
2905 unsigned long delta
= stream_get_endp(s
) + 24;
2906 struct ospf_lsa
*lsa
;
2908 rm_list
= list_new ();
2910 for (ALL_LIST_ELEMENTS_RO (ack
, node
, lsa
))
2912 lsa
= listgetdata (node
);
2915 if (length
+ delta
> ospf_packet_max (oi
))
2918 stream_put (s
, lsa
->data
, OSPF_LSA_HEADER_SIZE
);
2919 length
+= OSPF_LSA_HEADER_SIZE
;
2921 listnode_add (rm_list
, lsa
);
2924 /* Remove LSA from LS-Ack list. */
2925 /* XXX: this loop should be removed and the list move done in previous
2928 for (ALL_LIST_ELEMENTS_RO (rm_list
, node
, lsa
))
2930 listnode_delete (ack
, lsa
);
2931 ospf_lsa_unlock (lsa
);
2934 list_delete (rm_list
);
2940 ospf_hello_send_sub (struct ospf_interface
*oi
, struct in_addr
*addr
)
2942 struct ospf_packet
*op
;
2943 u_int16_t length
= OSPF_HEADER_SIZE
;
2945 op
= ospf_packet_new (oi
->ifp
->mtu
);
2947 /* Prepare OSPF common header. */
2948 ospf_make_header (OSPF_MSG_HELLO
, oi
, op
->s
);
2950 /* Prepare OSPF Hello body. */
2951 length
+= ospf_make_hello (oi
, op
->s
);
2953 /* Fill OSPF header. */
2954 ospf_fill_header (oi
, op
->s
, length
);
2956 /* Set packet length. */
2957 op
->length
= length
;
2959 op
->dst
.s_addr
= addr
->s_addr
;
2961 /* Add packet to the interface output queue. */
2962 ospf_packet_add (oi
, op
);
2964 /* Hook thread to write packet. */
2965 OSPF_ISM_WRITE_ON (oi
->ospf
);
2969 ospf_poll_send (struct ospf_nbr_nbma
*nbr_nbma
)
2971 struct ospf_interface
*oi
;
2976 /* If this is passive interface, do not send OSPF Hello. */
2977 if (OSPF_IF_PARAM (oi
, passive_interface
) == OSPF_IF_PASSIVE
)
2980 if (oi
->type
!= OSPF_IFTYPE_NBMA
)
2983 if (nbr_nbma
->nbr
!= NULL
&& nbr_nbma
->nbr
->state
!= NSM_Down
)
2986 if (PRIORITY(oi
) == 0)
2989 if (nbr_nbma
->priority
== 0
2990 && oi
->state
!= ISM_DR
&& oi
->state
!= ISM_Backup
)
2993 ospf_hello_send_sub (oi
, &nbr_nbma
->addr
);
2997 ospf_poll_timer (struct thread
*thread
)
2999 struct ospf_nbr_nbma
*nbr_nbma
;
3001 nbr_nbma
= THREAD_ARG (thread
);
3002 nbr_nbma
->t_poll
= NULL
;
3004 if (IS_DEBUG_OSPF (nsm
, NSM_TIMERS
))
3005 zlog (NULL
, LOG_DEBUG
, "NSM[%s:%s]: Timer (Poll timer expire)",
3006 IF_NAME (nbr_nbma
->oi
), inet_ntoa (nbr_nbma
->addr
));
3008 ospf_poll_send (nbr_nbma
);
3010 if (nbr_nbma
->v_poll
> 0)
3011 OSPF_POLL_TIMER_ON (nbr_nbma
->t_poll
, ospf_poll_timer
,
3019 ospf_hello_reply_timer (struct thread
*thread
)
3021 struct ospf_neighbor
*nbr
;
3023 nbr
= THREAD_ARG (thread
);
3024 nbr
->t_hello_reply
= NULL
;
3028 if (IS_DEBUG_OSPF (nsm
, NSM_TIMERS
))
3029 zlog (NULL
, LOG_DEBUG
, "NSM[%s:%s]: Timer (hello-reply timer expire)",
3030 IF_NAME (nbr
->oi
), inet_ntoa (nbr
->router_id
));
3032 ospf_hello_send_sub (nbr
->oi
, &nbr
->address
.u
.prefix4
);
3037 /* Send OSPF Hello. */
3039 ospf_hello_send (struct ospf_interface
*oi
)
3041 struct ospf_packet
*op
;
3042 u_int16_t length
= OSPF_HEADER_SIZE
;
3044 /* If this is passive interface, do not send OSPF Hello. */
3045 if (OSPF_IF_PARAM (oi
, passive_interface
) == OSPF_IF_PASSIVE
)
3048 op
= ospf_packet_new (oi
->ifp
->mtu
);
3050 /* Prepare OSPF common header. */
3051 ospf_make_header (OSPF_MSG_HELLO
, oi
, op
->s
);
3053 /* Prepare OSPF Hello body. */
3054 length
+= ospf_make_hello (oi
, op
->s
);
3056 /* Fill OSPF header. */
3057 ospf_fill_header (oi
, op
->s
, length
);
3059 /* Set packet length. */
3060 op
->length
= length
;
3062 if (oi
->type
== OSPF_IFTYPE_NBMA
)
3064 struct ospf_neighbor
*nbr
;
3065 struct route_node
*rn
;
3067 for (rn
= route_top (oi
->nbrs
); rn
; rn
= route_next (rn
))
3068 if ((nbr
= rn
->info
))
3069 if (nbr
!= oi
->nbr_self
)
3070 if (nbr
->state
!= NSM_Down
)
3072 /* RFC 2328 Section 9.5.1
3073 If the router is not eligible to become Designated Router,
3074 it must periodically send Hello Packets to both the
3075 Designated Router and the Backup Designated Router (if they
3077 if (PRIORITY(oi
) == 0 &&
3078 IPV4_ADDR_CMP(&DR(oi
), &nbr
->address
.u
.prefix4
) &&
3079 IPV4_ADDR_CMP(&BDR(oi
), &nbr
->address
.u
.prefix4
))
3082 /* If the router is eligible to become Designated Router, it
3083 must periodically send Hello Packets to all neighbors that
3084 are also eligible. In addition, if the router is itself the
3085 Designated Router or Backup Designated Router, it must also
3086 send periodic Hello Packets to all other neighbors. */
3088 if (nbr
->priority
== 0 && oi
->state
== ISM_DROther
)
3090 /* if oi->state == Waiting, send hello to all neighbors */
3092 struct ospf_packet
*op_dup
;
3094 op_dup
= ospf_packet_dup(op
);
3095 op_dup
->dst
= nbr
->address
.u
.prefix4
;
3097 /* Add packet to the interface output queue. */
3098 ospf_packet_add (oi
, op_dup
);
3100 OSPF_ISM_WRITE_ON (oi
->ospf
);
3104 ospf_packet_free (op
);
3108 /* Decide destination address. */
3109 if (oi
->type
== OSPF_IFTYPE_VIRTUALLINK
)
3110 op
->dst
.s_addr
= oi
->vl_data
->peer_addr
.s_addr
;
3112 op
->dst
.s_addr
= htonl (OSPF_ALLSPFROUTERS
);
3114 /* Add packet to the interface output queue. */
3115 ospf_packet_add (oi
, op
);
3117 /* Hook thread to write packet. */
3118 OSPF_ISM_WRITE_ON (oi
->ospf
);
3122 /* Send OSPF Database Description. */
3124 ospf_db_desc_send (struct ospf_neighbor
*nbr
)
3126 struct ospf_interface
*oi
;
3127 struct ospf_packet
*op
;
3128 u_int16_t length
= OSPF_HEADER_SIZE
;
3131 op
= ospf_packet_new (oi
->ifp
->mtu
);
3133 /* Prepare OSPF common header. */
3134 ospf_make_header (OSPF_MSG_DB_DESC
, oi
, op
->s
);
3136 /* Prepare OSPF Database Description body. */
3137 length
+= ospf_make_db_desc (oi
, nbr
, op
->s
);
3139 /* Fill OSPF header. */
3140 ospf_fill_header (oi
, op
->s
, length
);
3142 /* Set packet length. */
3143 op
->length
= length
;
3145 /* Decide destination address. */
3146 op
->dst
= nbr
->address
.u
.prefix4
;
3148 /* Add packet to the interface output queue. */
3149 ospf_packet_add (oi
, op
);
3151 /* Hook thread to write packet. */
3152 OSPF_ISM_WRITE_ON (oi
->ospf
);
3154 /* Remove old DD packet, then copy new one and keep in neighbor structure. */
3156 ospf_packet_free (nbr
->last_send
);
3157 nbr
->last_send
= ospf_packet_dup (op
);
3158 gettimeofday (&nbr
->last_send_ts
, NULL
);
3161 /* Re-send Database Description. */
3163 ospf_db_desc_resend (struct ospf_neighbor
*nbr
)
3165 struct ospf_interface
*oi
;
3169 /* Add packet to the interface output queue. */
3170 ospf_packet_add (oi
, ospf_packet_dup (nbr
->last_send
));
3172 /* Hook thread to write packet. */
3173 OSPF_ISM_WRITE_ON (oi
->ospf
);
3176 /* Send Link State Request. */
3178 ospf_ls_req_send (struct ospf_neighbor
*nbr
)
3180 struct ospf_interface
*oi
;
3181 struct ospf_packet
*op
;
3182 u_int16_t length
= OSPF_HEADER_SIZE
;
3185 op
= ospf_packet_new (oi
->ifp
->mtu
);
3187 /* Prepare OSPF common header. */
3188 ospf_make_header (OSPF_MSG_LS_REQ
, oi
, op
->s
);
3190 /* Prepare OSPF Link State Request body. */
3191 length
+= ospf_make_ls_req (nbr
, op
->s
);
3192 if (length
== OSPF_HEADER_SIZE
)
3194 ospf_packet_free (op
);
3198 /* Fill OSPF header. */
3199 ospf_fill_header (oi
, op
->s
, length
);
3201 /* Set packet length. */
3202 op
->length
= length
;
3204 /* Decide destination address. */
3205 op
->dst
= nbr
->address
.u
.prefix4
;
3207 /* Add packet to the interface output queue. */
3208 ospf_packet_add (oi
, op
);
3210 /* Hook thread to write packet. */
3211 OSPF_ISM_WRITE_ON (oi
->ospf
);
3213 /* Add Link State Request Retransmission Timer. */
3214 OSPF_NSM_TIMER_ON (nbr
->t_ls_req
, ospf_ls_req_timer
, nbr
->v_ls_req
);
3217 /* Send Link State Update with an LSA. */
3219 ospf_ls_upd_send_lsa (struct ospf_neighbor
*nbr
, struct ospf_lsa
*lsa
,
3222 struct list
*update
;
3224 update
= list_new ();
3226 listnode_add (update
, lsa
);
3227 ospf_ls_upd_send (nbr
, update
, flag
);
3229 list_delete (update
);
3232 /* Determine size for packet. Must be at least big enough to accomodate next
3233 * LSA on list, which may be bigger than MTU size.
3235 * Return pointer to new ospf_packet
3236 * NULL if we can not allocate, eg because LSA is bigger than imposed limit
3237 * on packet sizes (in which case offending LSA is deleted from update list)
3239 static struct ospf_packet
*
3240 ospf_ls_upd_packet_new (struct list
*update
, struct ospf_interface
*oi
)
3242 struct ospf_lsa
*lsa
;
3243 struct listnode
*ln
;
3245 static char warned
= 0;
3247 lsa
= listgetdata((ln
= listhead (update
)));
3250 if ((OSPF_LS_UPD_MIN_SIZE
+ ntohs (lsa
->data
->length
))
3251 > ospf_packet_max (oi
))
3255 zlog_warn ("ospf_ls_upd_packet_new: oversized LSA encountered!"
3256 "will need to fragment. Not optimal. Try divide up"
3257 " your network with areas. Use 'debug ospf packet send'"
3258 " to see details, or look at 'show ip ospf database ..'");
3262 if (IS_DEBUG_OSPF_PACKET (0, SEND
))
3263 zlog_debug ("ospf_ls_upd_packet_new: oversized LSA id:%s,"
3264 " %d bytes originated by %s, will be fragmented!",
3265 inet_ntoa (lsa
->data
->id
),
3266 ntohs (lsa
->data
->length
),
3267 inet_ntoa (lsa
->data
->adv_router
));
3270 * Allocate just enough to fit this LSA only, to avoid including other
3271 * LSAs in fragmented LSA Updates.
3273 size
= ntohs (lsa
->data
->length
) + (oi
->ifp
->mtu
- ospf_packet_max (oi
))
3274 + OSPF_LS_UPD_MIN_SIZE
;
3277 size
= oi
->ifp
->mtu
;
3279 /* XXX Should this be - sizeof(struct ip)?? -gdt */
3280 if (size
> OSPF_MAX_PACKET_SIZE
)
3282 zlog_warn ("ospf_ls_upd_packet_new: oversized LSA id:%s too big,"
3283 " %d bytes, packet size %ld, dropping it completely."
3284 " OSPF routing is broken!",
3285 inet_ntoa (lsa
->data
->id
), ntohs (lsa
->data
->length
),
3287 list_delete_node (update
, ln
);
3291 return ospf_packet_new (size
);
3295 ospf_ls_upd_queue_send (struct ospf_interface
*oi
, struct list
*update
,
3296 struct in_addr addr
)
3298 struct ospf_packet
*op
;
3299 u_int16_t length
= OSPF_HEADER_SIZE
;
3301 if (IS_DEBUG_OSPF_EVENT
)
3302 zlog_debug ("listcount = %d, dst %s", listcount (update
), inet_ntoa(addr
));
3304 op
= ospf_ls_upd_packet_new (update
, oi
);
3306 /* Prepare OSPF common header. */
3307 ospf_make_header (OSPF_MSG_LS_UPD
, oi
, op
->s
);
3309 /* Prepare OSPF Link State Update body.
3310 * Includes Type-7 translation.
3312 length
+= ospf_make_ls_upd (oi
, update
, op
->s
);
3314 /* Fill OSPF header. */
3315 ospf_fill_header (oi
, op
->s
, length
);
3317 /* Set packet length. */
3318 op
->length
= length
;
3320 /* Decide destination address. */
3321 op
->dst
.s_addr
= addr
.s_addr
;
3323 /* Add packet to the interface output queue. */
3324 ospf_packet_add (oi
, op
);
3326 /* Hook thread to write packet. */
3327 OSPF_ISM_WRITE_ON (oi
->ospf
);
3331 ospf_ls_upd_send_queue_event (struct thread
*thread
)
3333 struct ospf_interface
*oi
= THREAD_ARG(thread
);
3334 struct route_node
*rn
;
3335 struct route_node
*rnext
;
3336 struct list
*update
;
3339 oi
->t_ls_upd_event
= NULL
;
3341 if (IS_DEBUG_OSPF_EVENT
)
3342 zlog_debug ("ospf_ls_upd_send_queue start");
3344 for (rn
= route_top (oi
->ls_upd_queue
); rn
; rn
= rnext
)
3346 rnext
= route_next (rn
);
3348 if (rn
->info
== NULL
)
3351 update
= (struct list
*)rn
->info
;
3353 ospf_ls_upd_queue_send (oi
, update
, rn
->p
.u
.prefix4
);
3355 /* list might not be empty. */
3356 if (listcount(update
) == 0)
3358 list_delete (rn
->info
);
3360 route_unlock_node (rn
);
3368 if (IS_DEBUG_OSPF_EVENT
)
3369 zlog_debug ("ospf_ls_upd_send_queue: update lists not cleared,"
3370 " %d nodes to try again, raising new event", again
);
3371 oi
->t_ls_upd_event
=
3372 thread_add_event (master
, ospf_ls_upd_send_queue_event
, oi
, 0);
3375 if (IS_DEBUG_OSPF_EVENT
)
3376 zlog_debug ("ospf_ls_upd_send_queue stop");
3382 ospf_ls_upd_send (struct ospf_neighbor
*nbr
, struct list
*update
, int flag
)
3384 struct ospf_interface
*oi
;
3385 struct ospf_lsa
*lsa
;
3386 struct prefix_ipv4 p
;
3387 struct route_node
*rn
;
3388 struct listnode
*node
;
3393 p
.prefixlen
= IPV4_MAX_BITLEN
;
3395 /* Decide destination address. */
3396 if (oi
->type
== OSPF_IFTYPE_VIRTUALLINK
)
3397 p
.prefix
= oi
->vl_data
->peer_addr
;
3398 else if (flag
== OSPF_SEND_PACKET_DIRECT
)
3399 p
.prefix
= nbr
->address
.u
.prefix4
;
3400 else if (oi
->state
== ISM_DR
|| oi
->state
== ISM_Backup
)
3401 p
.prefix
.s_addr
= htonl (OSPF_ALLSPFROUTERS
);
3402 else if ((oi
->type
== OSPF_IFTYPE_POINTOPOINT
)
3403 && (flag
== OSPF_SEND_PACKET_INDIRECT
))
3404 p
.prefix
.s_addr
= htonl (OSPF_ALLSPFROUTERS
);
3405 else if (oi
->type
== OSPF_IFTYPE_POINTOMULTIPOINT
)
3406 p
.prefix
.s_addr
= htonl (OSPF_ALLSPFROUTERS
);
3408 p
.prefix
.s_addr
= htonl (OSPF_ALLDROUTERS
);
3410 if (oi
->type
== OSPF_IFTYPE_NBMA
)
3412 if (flag
== OSPF_SEND_PACKET_INDIRECT
)
3413 zlog_warn ("* LS-Update is directly sent on NBMA network.");
3414 if (IPV4_ADDR_SAME(&oi
->address
->u
.prefix4
, &p
.prefix
.s_addr
))
3415 zlog_warn ("* LS-Update is sent to myself.");
3418 rn
= route_node_get (oi
->ls_upd_queue
, (struct prefix
*) &p
);
3420 if (rn
->info
== NULL
)
3421 rn
->info
= list_new ();
3423 for (ALL_LIST_ELEMENTS_RO (update
, node
, lsa
))
3425 ospf_lsa_lock (lsa
);
3426 listnode_add (rn
->info
, lsa
);
3429 if (oi
->t_ls_upd_event
== NULL
)
3430 oi
->t_ls_upd_event
=
3431 thread_add_event (master
, ospf_ls_upd_send_queue_event
, oi
, 0);
3435 ospf_ls_ack_send_list (struct ospf_interface
*oi
, struct list
*ack
,
3438 struct ospf_packet
*op
;
3439 u_int16_t length
= OSPF_HEADER_SIZE
;
3441 op
= ospf_packet_new (oi
->ifp
->mtu
);
3443 /* Prepare OSPF common header. */
3444 ospf_make_header (OSPF_MSG_LS_ACK
, oi
, op
->s
);
3446 /* Prepare OSPF Link State Acknowledgment body. */
3447 length
+= ospf_make_ls_ack (oi
, ack
, op
->s
);
3449 /* Fill OSPF header. */
3450 ospf_fill_header (oi
, op
->s
, length
);
3452 /* Set packet length. */
3453 op
->length
= length
;
3455 /* Set destination IP address. */
3458 /* Add packet to the interface output queue. */
3459 ospf_packet_add (oi
, op
);
3461 /* Hook thread to write packet. */
3462 OSPF_ISM_WRITE_ON (oi
->ospf
);
3466 ospf_ls_ack_send_event (struct thread
*thread
)
3468 struct ospf_interface
*oi
= THREAD_ARG (thread
);
3470 oi
->t_ls_ack_direct
= NULL
;
3472 while (listcount (oi
->ls_ack_direct
.ls_ack
))
3473 ospf_ls_ack_send_list (oi
, oi
->ls_ack_direct
.ls_ack
,
3474 oi
->ls_ack_direct
.dst
);
3480 ospf_ls_ack_send (struct ospf_neighbor
*nbr
, struct ospf_lsa
*lsa
)
3482 struct ospf_interface
*oi
= nbr
->oi
;
3484 if (listcount (oi
->ls_ack_direct
.ls_ack
) == 0)
3485 oi
->ls_ack_direct
.dst
= nbr
->address
.u
.prefix4
;
3487 listnode_add (oi
->ls_ack_direct
.ls_ack
, ospf_lsa_lock (lsa
));
3489 if (oi
->t_ls_ack_direct
== NULL
)
3490 oi
->t_ls_ack_direct
=
3491 thread_add_event (master
, ospf_ls_ack_send_event
, oi
, 0);
3494 /* Send Link State Acknowledgment delayed. */
3496 ospf_ls_ack_send_delayed (struct ospf_interface
*oi
)
3500 /* Decide destination address. */
3501 /* RFC2328 Section 13.5 On non-broadcast
3502 networks, delayed Link State Acknowledgment packets must be
3503 unicast separately over each adjacency (i.e., neighbor whose
3504 state is >= Exchange). */
3505 if (oi
->type
== OSPF_IFTYPE_NBMA
)
3507 struct ospf_neighbor
*nbr
;
3508 struct route_node
*rn
;
3510 for (rn
= route_top (oi
->nbrs
); rn
; rn
= route_next (rn
))
3511 if ((nbr
= rn
->info
) != NULL
)
3512 if (nbr
!= oi
->nbr_self
&& nbr
->state
>= NSM_Exchange
)
3513 while (listcount (oi
->ls_ack
))
3514 ospf_ls_ack_send_list (oi
, oi
->ls_ack
, nbr
->address
.u
.prefix4
);
3517 if (oi
->type
== OSPF_IFTYPE_VIRTUALLINK
)
3518 dst
.s_addr
= oi
->vl_data
->peer_addr
.s_addr
;
3519 else if (oi
->state
== ISM_DR
|| oi
->state
== ISM_Backup
)
3520 dst
.s_addr
= htonl (OSPF_ALLSPFROUTERS
);
3521 else if (oi
->type
== OSPF_IFTYPE_POINTOPOINT
)
3522 dst
.s_addr
= htonl (OSPF_ALLSPFROUTERS
);
3523 else if (oi
->type
== OSPF_IFTYPE_POINTOMULTIPOINT
)
3524 dst
.s_addr
= htonl (OSPF_ALLSPFROUTERS
);
3526 dst
.s_addr
= htonl (OSPF_ALLDROUTERS
);
3528 while (listcount (oi
->ls_ack
))
3529 ospf_ls_ack_send_list (oi
, oi
->ls_ack
, dst
);