1: /*
2: * OSPF Sending and Receiving OSPF Packets.
3: * Copyright (C) 1999, 2000 Toshiaki Takada
4: *
5: * This file is part of GNU Zebra.
6: *
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
10: * later version.
11: *
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.
16: *
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
20: * 02111-1307, USA.
21: */
22:
23: #include <zebra.h>
24:
25: #include "thread.h"
26: #include "memory.h"
27: #include "linklist.h"
28: #include "prefix.h"
29: #include "if.h"
30: #include "table.h"
31: #include "sockunion.h"
32: #include "stream.h"
33: #include "log.h"
34: #include "sockopt.h"
35: #include "checksum.h"
36: #include "md5.h"
37:
38: #include "ospfd/ospfd.h"
39: #include "ospfd/ospf_network.h"
40: #include "ospfd/ospf_interface.h"
41: #include "ospfd/ospf_ism.h"
42: #include "ospfd/ospf_asbr.h"
43: #include "ospfd/ospf_lsa.h"
44: #include "ospfd/ospf_lsdb.h"
45: #include "ospfd/ospf_neighbor.h"
46: #include "ospfd/ospf_nsm.h"
47: #include "ospfd/ospf_packet.h"
48: #include "ospfd/ospf_spf.h"
49: #include "ospfd/ospf_flood.h"
50: #include "ospfd/ospf_dump.h"
51:
52: /* Packet Type String. */
53: const struct message ospf_packet_type_str[] =
54: {
55: { OSPF_MSG_HELLO, "Hello" },
56: { OSPF_MSG_DB_DESC, "Database Description" },
57: { OSPF_MSG_LS_REQ, "Link State Request" },
58: { OSPF_MSG_LS_UPD, "Link State Update" },
59: { OSPF_MSG_LS_ACK, "Link State Acknowledgment" },
60: };
61: const size_t ospf_packet_type_str_max = sizeof (ospf_packet_type_str) /
62: sizeof (ospf_packet_type_str[0]);
63:
64: /* Minimum (besides OSPF_HEADER_SIZE) lengths for OSPF packets of
65: particular types, offset is the "type" field of a packet. */
66: static const u_int16_t ospf_packet_minlen[] =
67: {
68: 0,
69: OSPF_HELLO_MIN_SIZE,
70: OSPF_DB_DESC_MIN_SIZE,
71: OSPF_LS_REQ_MIN_SIZE,
72: OSPF_LS_UPD_MIN_SIZE,
73: OSPF_LS_ACK_MIN_SIZE,
74: };
75:
76: /* Minimum (besides OSPF_LSA_HEADER_SIZE) lengths for LSAs of particular
77: types, offset is the "LSA type" field. */
78: static const u_int16_t ospf_lsa_minlen[] =
79: {
80: 0,
81: OSPF_ROUTER_LSA_MIN_SIZE,
82: OSPF_NETWORK_LSA_MIN_SIZE,
83: OSPF_SUMMARY_LSA_MIN_SIZE,
84: OSPF_SUMMARY_LSA_MIN_SIZE,
85: OSPF_AS_EXTERNAL_LSA_MIN_SIZE,
86: 0,
87: OSPF_AS_EXTERNAL_LSA_MIN_SIZE,
88: 0,
89: 0,
90: 0,
91: 0,
92: };
93:
94: /* for ospf_check_auth() */
95: static int ospf_check_sum (struct ospf_header *);
96:
97: /* OSPF authentication checking function */
98: static int
99: ospf_auth_type (struct ospf_interface *oi)
100: {
101: int auth_type;
102:
103: if (OSPF_IF_PARAM (oi, auth_type) == OSPF_AUTH_NOTSET)
104: auth_type = oi->area->auth_type;
105: else
106: auth_type = OSPF_IF_PARAM (oi, auth_type);
107:
108: /* Handle case where MD5 key list is not configured aka Cisco */
109: if (auth_type == OSPF_AUTH_CRYPTOGRAPHIC &&
110: list_isempty (OSPF_IF_PARAM (oi, auth_crypt)))
111: return OSPF_AUTH_NULL;
112:
113: return auth_type;
114:
115: }
116:
117: struct ospf_packet *
118: ospf_packet_new (size_t size)
119: {
120: struct ospf_packet *new;
121:
122: new = XCALLOC (MTYPE_OSPF_PACKET, sizeof (struct ospf_packet));
123: new->s = stream_new (size);
124:
125: return new;
126: }
127:
128: void
129: ospf_packet_free (struct ospf_packet *op)
130: {
131: if (op->s)
132: stream_free (op->s);
133:
134: XFREE (MTYPE_OSPF_PACKET, op);
135:
136: op = NULL;
137: }
138:
139: struct ospf_fifo *
140: ospf_fifo_new ()
141: {
142: struct ospf_fifo *new;
143:
144: new = XCALLOC (MTYPE_OSPF_FIFO, sizeof (struct ospf_fifo));
145: return new;
146: }
147:
148: /* Add new packet to fifo. */
149: void
150: ospf_fifo_push (struct ospf_fifo *fifo, struct ospf_packet *op)
151: {
152: if (fifo->tail)
153: fifo->tail->next = op;
154: else
155: fifo->head = op;
156:
157: fifo->tail = op;
158:
159: fifo->count++;
160: }
161:
162: /* Add new packet to head of fifo. */
163: static void
164: ospf_fifo_push_head (struct ospf_fifo *fifo, struct ospf_packet *op)
165: {
166: op->next = fifo->head;
167:
168: if (fifo->tail == NULL)
169: fifo->tail = op;
170:
171: fifo->head = op;
172:
173: fifo->count++;
174: }
175:
176: /* Delete first packet from fifo. */
177: struct ospf_packet *
178: ospf_fifo_pop (struct ospf_fifo *fifo)
179: {
180: struct ospf_packet *op;
181:
182: op = fifo->head;
183:
184: if (op)
185: {
186: fifo->head = op->next;
187:
188: if (fifo->head == NULL)
189: fifo->tail = NULL;
190:
191: fifo->count--;
192: }
193:
194: return op;
195: }
196:
197: /* Return first fifo entry. */
198: struct ospf_packet *
199: ospf_fifo_head (struct ospf_fifo *fifo)
200: {
201: return fifo->head;
202: }
203:
204: /* Flush ospf packet fifo. */
205: void
206: ospf_fifo_flush (struct ospf_fifo *fifo)
207: {
208: struct ospf_packet *op;
209: struct ospf_packet *next;
210:
211: for (op = fifo->head; op; op = next)
212: {
213: next = op->next;
214: ospf_packet_free (op);
215: }
216: fifo->head = fifo->tail = NULL;
217: fifo->count = 0;
218: }
219:
220: /* Free ospf packet fifo. */
221: void
222: ospf_fifo_free (struct ospf_fifo *fifo)
223: {
224: ospf_fifo_flush (fifo);
225:
226: XFREE (MTYPE_OSPF_FIFO, fifo);
227: }
228:
229: void
230: ospf_packet_add (struct ospf_interface *oi, struct ospf_packet *op)
231: {
232: if (!oi->obuf)
233: {
234: zlog_err("ospf_packet_add(interface %s in state %d [%s], packet type %s, "
235: "destination %s) called with NULL obuf, ignoring "
236: "(please report this bug)!\n",
237: IF_NAME(oi), oi->state, LOOKUP (ospf_ism_state_msg, oi->state),
238: LOOKUP (ospf_packet_type_str, stream_getc_from(op->s, 1)),
239: inet_ntoa (op->dst));
240: return;
241: }
242:
243: /* Add packet to end of queue. */
244: ospf_fifo_push (oi->obuf, op);
245:
246: /* Debug of packet fifo*/
247: /* ospf_fifo_debug (oi->obuf); */
248: }
249:
250: static void
251: ospf_packet_add_top (struct ospf_interface *oi, struct ospf_packet *op)
252: {
253: if (!oi->obuf)
254: {
255: zlog_err("ospf_packet_add(interface %s in state %d [%s], packet type %s, "
256: "destination %s) called with NULL obuf, ignoring "
257: "(please report this bug)!\n",
258: IF_NAME(oi), oi->state, LOOKUP (ospf_ism_state_msg, oi->state),
259: LOOKUP (ospf_packet_type_str, stream_getc_from(op->s, 1)),
260: inet_ntoa (op->dst));
261: return;
262: }
263:
264: /* Add packet to head of queue. */
265: ospf_fifo_push_head (oi->obuf, op);
266:
267: /* Debug of packet fifo*/
268: /* ospf_fifo_debug (oi->obuf); */
269: }
270:
271: void
272: ospf_packet_delete (struct ospf_interface *oi)
273: {
274: struct ospf_packet *op;
275:
276: op = ospf_fifo_pop (oi->obuf);
277:
278: if (op)
279: ospf_packet_free (op);
280: }
281:
282: struct ospf_packet *
283: ospf_packet_dup (struct ospf_packet *op)
284: {
285: struct ospf_packet *new;
286:
287: if (stream_get_endp(op->s) != op->length)
288: /* XXX size_t */
289: zlog_warn ("ospf_packet_dup stream %lu ospf_packet %u size mismatch",
290: (u_long)STREAM_SIZE(op->s), op->length);
291:
292: /* Reserve space for MD5 authentication that may be added later. */
293: new = ospf_packet_new (stream_get_endp(op->s) + OSPF_AUTH_MD5_SIZE);
294: stream_copy (new->s, op->s);
295:
296: new->dst = op->dst;
297: new->length = op->length;
298:
299: return new;
300: }
301:
302: /* XXX inline */
303: static inline unsigned int
304: ospf_packet_authspace (struct ospf_interface *oi)
305: {
306: int auth = 0;
307:
308: if ( ospf_auth_type (oi) == OSPF_AUTH_CRYPTOGRAPHIC)
309: auth = OSPF_AUTH_MD5_SIZE;
310:
311: return auth;
312: }
313:
314: static unsigned int
315: ospf_packet_max (struct ospf_interface *oi)
316: {
317: int max;
318:
319: max = oi->ifp->mtu - ospf_packet_authspace(oi);
320:
321: max -= (OSPF_HEADER_SIZE + sizeof (struct ip));
322:
323: return max;
324: }
325:
326:
327: static int
328: ospf_check_md5_digest (struct ospf_interface *oi, struct ospf_header *ospfh)
329: {
330: MD5_CTX ctx;
331: unsigned char digest[OSPF_AUTH_MD5_SIZE];
332: struct crypt_key *ck;
333: struct ospf_neighbor *nbr;
334: u_int16_t length = ntohs (ospfh->length);
335:
336: /* Get secret key. */
337: ck = ospf_crypt_key_lookup (OSPF_IF_PARAM (oi, auth_crypt),
338: ospfh->u.crypt.key_id);
339: if (ck == NULL)
340: {
341: zlog_warn ("interface %s: ospf_check_md5 no key %d",
342: IF_NAME (oi), ospfh->u.crypt.key_id);
343: return 0;
344: }
345:
346: /* check crypto seqnum. */
347: nbr = ospf_nbr_lookup_by_routerid (oi->nbrs, &ospfh->router_id);
348:
349: if (nbr && ntohl(nbr->crypt_seqnum) > ntohl(ospfh->u.crypt.crypt_seqnum))
350: {
351: zlog_warn ("interface %s: ospf_check_md5 bad sequence %d (expect %d)",
352: IF_NAME (oi),
353: ntohl(ospfh->u.crypt.crypt_seqnum),
354: ntohl(nbr->crypt_seqnum));
355: return 0;
356: }
357:
358: /* Generate a digest for the ospf packet - their digest + our digest. */
359: memset(&ctx, 0, sizeof(ctx));
360: MD5Init(&ctx);
361: MD5Update(&ctx, ospfh, length);
362: MD5Update(&ctx, ck->auth_key, OSPF_AUTH_MD5_SIZE);
363: MD5Final(digest, &ctx);
364:
365: /* compare the two */
366: if (memcmp ((caddr_t)ospfh + length, digest, OSPF_AUTH_MD5_SIZE))
367: {
368: zlog_warn ("interface %s: ospf_check_md5 checksum mismatch",
369: IF_NAME (oi));
370: return 0;
371: }
372:
373: /* save neighbor's crypt_seqnum */
374: if (nbr)
375: nbr->crypt_seqnum = ospfh->u.crypt.crypt_seqnum;
376: return 1;
377: }
378:
379: /* This function is called from ospf_write(), it will detect the
380: authentication scheme and if it is MD5, it will change the sequence
381: and update the MD5 digest. */
382: static int
383: ospf_make_md5_digest (struct ospf_interface *oi, struct ospf_packet *op)
384: {
385: struct ospf_header *ospfh;
386: unsigned char digest[OSPF_AUTH_MD5_SIZE];
387: MD5_CTX ctx;
388: void *ibuf;
389: u_int32_t t;
390: struct crypt_key *ck;
391: const u_int8_t *auth_key;
392:
393: ibuf = STREAM_DATA (op->s);
394: ospfh = (struct ospf_header *) ibuf;
395:
396: if (ntohs (ospfh->auth_type) != OSPF_AUTH_CRYPTOGRAPHIC)
397: return 0;
398:
399: /* We do this here so when we dup a packet, we don't have to
400: waste CPU rewriting other headers.
401:
402: Note that quagga_time /deliberately/ is not used here */
403: t = (time(NULL) & 0xFFFFFFFF);
404: if (t > oi->crypt_seqnum)
405: oi->crypt_seqnum = t;
406: else
407: oi->crypt_seqnum++;
408:
409: ospfh->u.crypt.crypt_seqnum = htonl (oi->crypt_seqnum);
410:
411: /* Get MD5 Authentication key from auth_key list. */
412: if (list_isempty (OSPF_IF_PARAM (oi, auth_crypt)))
413: auth_key = (const u_int8_t *) "";
414: else
415: {
416: ck = listgetdata (listtail(OSPF_IF_PARAM (oi, auth_crypt)));
417: auth_key = ck->auth_key;
418: }
419:
420: /* Generate a digest for the entire packet + our secret key. */
421: memset(&ctx, 0, sizeof(ctx));
422: MD5Init(&ctx);
423: MD5Update(&ctx, ibuf, ntohs (ospfh->length));
424: MD5Update(&ctx, auth_key, OSPF_AUTH_MD5_SIZE);
425: MD5Final(digest, &ctx);
426:
427: /* Append md5 digest to the end of the stream. */
428: stream_put (op->s, digest, OSPF_AUTH_MD5_SIZE);
429:
430: /* We do *NOT* increment the OSPF header length. */
431: op->length = ntohs (ospfh->length) + OSPF_AUTH_MD5_SIZE;
432:
433: if (stream_get_endp(op->s) != op->length)
434: /* XXX size_t */
435: zlog_warn("ospf_make_md5_digest: length mismatch stream %lu ospf_packet %u",
436: (u_long)stream_get_endp(op->s), op->length);
437:
438: return OSPF_AUTH_MD5_SIZE;
439: }
440:
441:
442: static int
443: ospf_ls_req_timer (struct thread *thread)
444: {
445: struct ospf_neighbor *nbr;
446:
447: nbr = THREAD_ARG (thread);
448: nbr->t_ls_req = NULL;
449:
450: /* Send Link State Request. */
451: if (ospf_ls_request_count (nbr))
452: ospf_ls_req_send (nbr);
453:
454: /* Set Link State Request retransmission timer. */
455: OSPF_NSM_TIMER_ON (nbr->t_ls_req, ospf_ls_req_timer, nbr->v_ls_req);
456:
457: return 0;
458: }
459:
460: void
461: ospf_ls_req_event (struct ospf_neighbor *nbr)
462: {
463: if (nbr->t_ls_req)
464: {
465: thread_cancel (nbr->t_ls_req);
466: nbr->t_ls_req = NULL;
467: }
468: nbr->t_ls_req = thread_add_event (master, ospf_ls_req_timer, nbr, 0);
469: }
470:
471: /* Cyclic timer function. Fist registered in ospf_nbr_new () in
472: ospf_neighbor.c */
473: int
474: ospf_ls_upd_timer (struct thread *thread)
475: {
476: struct ospf_neighbor *nbr;
477:
478: nbr = THREAD_ARG (thread);
479: nbr->t_ls_upd = NULL;
480:
481: /* Send Link State Update. */
482: if (ospf_ls_retransmit_count (nbr) > 0)
483: {
484: struct list *update;
485: struct ospf_lsdb *lsdb;
486: int i;
487: int retransmit_interval;
488:
489: retransmit_interval = OSPF_IF_PARAM (nbr->oi, retransmit_interval);
490:
491: lsdb = &nbr->ls_rxmt;
492: update = list_new ();
493:
494: for (i = OSPF_MIN_LSA; i < OSPF_MAX_LSA; i++)
495: {
496: struct route_table *table = lsdb->type[i].db;
497: struct route_node *rn;
498:
499: for (rn = route_top (table); rn; rn = route_next (rn))
500: {
501: struct ospf_lsa *lsa;
502:
503: if ((lsa = rn->info) != NULL)
504: /* Don't retransmit an LSA if we received it within
505: the last RxmtInterval seconds - this is to allow the
506: neighbour a chance to acknowledge the LSA as it may
507: have ben just received before the retransmit timer
508: fired. This is a small tweak to what is in the RFC,
509: but it will cut out out a lot of retransmit traffic
510: - MAG */
511: if (tv_cmp (tv_sub (recent_relative_time (), lsa->tv_recv),
512: int2tv (retransmit_interval)) >= 0)
513: listnode_add (update, rn->info);
514: }
515: }
516:
517: if (listcount (update) > 0)
518: ospf_ls_upd_send (nbr, update, OSPF_SEND_PACKET_DIRECT);
519: list_delete (update);
520: }
521:
522: /* Set LS Update retransmission timer. */
523: OSPF_NSM_TIMER_ON (nbr->t_ls_upd, ospf_ls_upd_timer, nbr->v_ls_upd);
524:
525: return 0;
526: }
527:
528: int
529: ospf_ls_ack_timer (struct thread *thread)
530: {
531: struct ospf_interface *oi;
532:
533: oi = THREAD_ARG (thread);
534: oi->t_ls_ack = NULL;
535:
536: /* Send Link State Acknowledgment. */
537: if (listcount (oi->ls_ack) > 0)
538: ospf_ls_ack_send_delayed (oi);
539:
540: /* Set LS Ack timer. */
541: OSPF_ISM_TIMER_ON (oi->t_ls_ack, ospf_ls_ack_timer, oi->v_ls_ack);
542:
543: return 0;
544: }
545:
546: #ifdef WANT_OSPF_WRITE_FRAGMENT
547: static void
548: ospf_write_frags (int fd, struct ospf_packet *op, struct ip *iph,
549: struct msghdr *msg, unsigned int maxdatasize,
550: unsigned int mtu, int flags, u_char type)
551: {
552: #define OSPF_WRITE_FRAG_SHIFT 3
553: u_int16_t offset;
554: struct iovec *iovp;
555: int ret;
556:
557: assert ( op->length == stream_get_endp(op->s) );
558: assert (msg->msg_iovlen == 2);
559:
560: /* we can but try.
561: *
562: * SunOS, BSD and BSD derived kernels likely will clear ip_id, as
563: * well as the IP_MF flag, making this all quite pointless.
564: *
565: * However, for a system on which IP_MF is left alone, and ip_id left
566: * alone or else which sets same ip_id for each fragment this might
567: * work, eg linux.
568: *
569: * XXX-TODO: It would be much nicer to have the kernel's use their
570: * existing fragmentation support to do this for us. Bugs/RFEs need to
571: * be raised against the various kernels.
572: */
573:
574: /* set More Frag */
575: iph->ip_off |= IP_MF;
576:
577: /* ip frag offset is expressed in units of 8byte words */
578: offset = maxdatasize >> OSPF_WRITE_FRAG_SHIFT;
579:
580: iovp = &msg->msg_iov[1];
581:
582: while ( (stream_get_endp(op->s) - stream_get_getp (op->s))
583: > maxdatasize )
584: {
585: /* data length of this frag is to next offset value */
586: iovp->iov_len = offset << OSPF_WRITE_FRAG_SHIFT;
587: iph->ip_len = iovp->iov_len + sizeof (struct ip);
588: assert (iph->ip_len <= mtu);
589:
590: sockopt_iphdrincl_swab_htosys (iph);
591:
592: ret = sendmsg (fd, msg, flags);
593:
594: sockopt_iphdrincl_swab_systoh (iph);
595:
596: if (ret < 0)
597: zlog_warn ("*** ospf_write_frags: sendmsg failed to %s,"
598: " id %d, off %d, len %d, mtu %u failed with %s",
599: inet_ntoa (iph->ip_dst),
600: iph->ip_id,
601: iph->ip_off,
602: iph->ip_len,
603: mtu,
604: safe_strerror (errno));
605:
606: if (IS_DEBUG_OSPF_PACKET (type - 1, SEND))
607: {
608: zlog_debug ("ospf_write_frags: sent id %d, off %d, len %d to %s\n",
609: iph->ip_id, iph->ip_off, iph->ip_len,
610: inet_ntoa (iph->ip_dst));
611: if (IS_DEBUG_OSPF_PACKET (type - 1, DETAIL))
612: {
613: zlog_debug ("-----------------IP Header Dump----------------------");
614: ospf_ip_header_dump (iph);
615: zlog_debug ("-----------------------------------------------------");
616: }
617: }
618:
619: iph->ip_off += offset;
620: stream_forward_getp (op->s, iovp->iov_len);
621: iovp->iov_base = STREAM_PNT (op->s);
622: }
623:
624: /* setup for final fragment */
625: iovp->iov_len = stream_get_endp(op->s) - stream_get_getp (op->s);
626: iph->ip_len = iovp->iov_len + sizeof (struct ip);
627: iph->ip_off &= (~IP_MF);
628: }
629: #endif /* WANT_OSPF_WRITE_FRAGMENT */
630:
631: static int
632: ospf_write (struct thread *thread)
633: {
634: struct ospf *ospf = THREAD_ARG (thread);
635: struct ospf_interface *oi;
636: struct ospf_packet *op;
637: struct sockaddr_in sa_dst;
638: struct ip iph;
639: struct msghdr msg;
640: struct iovec iov[2];
641: u_char type;
642: int ret;
643: int flags = 0;
644: struct listnode *node;
645: #ifdef WANT_OSPF_WRITE_FRAGMENT
646: static u_int16_t ipid = 0;
647: #endif /* WANT_OSPF_WRITE_FRAGMENT */
648: u_int16_t maxdatasize;
649: #define OSPF_WRITE_IPHL_SHIFT 2
650:
651: ospf->t_write = NULL;
652:
653: node = listhead (ospf->oi_write_q);
654: assert (node);
655: oi = listgetdata (node);
656: assert (oi);
657:
658: #ifdef WANT_OSPF_WRITE_FRAGMENT
659: /* seed ipid static with low order bits of time */
660: if (ipid == 0)
661: ipid = (time(NULL) & 0xffff);
662: #endif /* WANT_OSPF_WRITE_FRAGMENT */
663:
664: /* convenience - max OSPF data per packet,
665: * and reliability - not more data, than our
666: * socket can accept
667: */
668: maxdatasize = MIN (oi->ifp->mtu, ospf->maxsndbuflen) -
669: sizeof (struct ip);
670:
671: /* Get one packet from queue. */
672: op = ospf_fifo_head (oi->obuf);
673: assert (op);
674: assert (op->length >= OSPF_HEADER_SIZE);
675:
676: if (op->dst.s_addr == htonl (OSPF_ALLSPFROUTERS)
677: || op->dst.s_addr == htonl (OSPF_ALLDROUTERS))
678: ospf_if_ipmulticast (ospf, oi->address, oi->ifp->ifindex);
679:
680: /* Rewrite the md5 signature & update the seq */
681: ospf_make_md5_digest (oi, op);
682:
683: /* Retrieve OSPF packet type. */
684: stream_set_getp (op->s, 1);
685: type = stream_getc (op->s);
686:
687: /* reset get pointer */
688: stream_set_getp (op->s, 0);
689:
690: memset (&iph, 0, sizeof (struct ip));
691: memset (&sa_dst, 0, sizeof (sa_dst));
692:
693: sa_dst.sin_family = AF_INET;
694: #ifdef HAVE_STRUCT_SOCKADDR_IN_SIN_LEN
695: sa_dst.sin_len = sizeof(sa_dst);
696: #endif /* HAVE_STRUCT_SOCKADDR_IN_SIN_LEN */
697: sa_dst.sin_addr = op->dst;
698: sa_dst.sin_port = htons (0);
699:
700: /* Set DONTROUTE flag if dst is unicast. */
701: if (oi->type != OSPF_IFTYPE_VIRTUALLINK)
702: if (!IN_MULTICAST (htonl (op->dst.s_addr)))
703: flags = MSG_DONTROUTE;
704:
705: iph.ip_hl = sizeof (struct ip) >> OSPF_WRITE_IPHL_SHIFT;
706: /* it'd be very strange for header to not be 4byte-word aligned but.. */
707: if ( sizeof (struct ip)
708: > (unsigned int)(iph.ip_hl << OSPF_WRITE_IPHL_SHIFT) )
709: iph.ip_hl++; /* we presume sizeof struct ip cant overflow ip_hl.. */
710:
711: iph.ip_v = IPVERSION;
712: iph.ip_tos = IPTOS_PREC_INTERNETCONTROL;
713: iph.ip_len = (iph.ip_hl << OSPF_WRITE_IPHL_SHIFT) + op->length;
714:
715: #if defined(__DragonFly__)
716: /*
717: * DragonFly's raw socket expects ip_len/ip_off in network byte order.
718: */
719: iph.ip_len = htons(iph.ip_len);
720: #endif
721:
722: #ifdef WANT_OSPF_WRITE_FRAGMENT
723: /* XXX-MT: not thread-safe at all..
724: * XXX: this presumes this is only programme sending OSPF packets
725: * otherwise, no guarantee ipid will be unique
726: */
727: iph.ip_id = ++ipid;
728: #endif /* WANT_OSPF_WRITE_FRAGMENT */
729:
730: iph.ip_off = 0;
731: if (oi->type == OSPF_IFTYPE_VIRTUALLINK)
732: iph.ip_ttl = OSPF_VL_IP_TTL;
733: else
734: iph.ip_ttl = OSPF_IP_TTL;
735: iph.ip_p = IPPROTO_OSPFIGP;
736: iph.ip_sum = 0;
737: iph.ip_src.s_addr = oi->address->u.prefix4.s_addr;
738: iph.ip_dst.s_addr = op->dst.s_addr;
739:
740: memset (&msg, 0, sizeof (msg));
741: msg.msg_name = (caddr_t) &sa_dst;
742: msg.msg_namelen = sizeof (sa_dst);
743: msg.msg_iov = iov;
744: msg.msg_iovlen = 2;
745: iov[0].iov_base = (char*)&iph;
746: iov[0].iov_len = iph.ip_hl << OSPF_WRITE_IPHL_SHIFT;
747: iov[1].iov_base = STREAM_PNT (op->s);
748: iov[1].iov_len = op->length;
749:
750: /* Sadly we can not rely on kernels to fragment packets because of either
751: * IP_HDRINCL and/or multicast destination being set.
752: */
753: #ifdef WANT_OSPF_WRITE_FRAGMENT
754: if ( op->length > maxdatasize )
755: ospf_write_frags (ospf->fd, op, &iph, &msg, maxdatasize,
756: oi->ifp->mtu, flags, type);
757: #endif /* WANT_OSPF_WRITE_FRAGMENT */
758:
759: /* send final fragment (could be first) */
760: sockopt_iphdrincl_swab_htosys (&iph);
761: ret = sendmsg (ospf->fd, &msg, flags);
762: sockopt_iphdrincl_swab_systoh (&iph);
763:
764: if (ret < 0)
765: zlog_warn ("*** sendmsg in ospf_write failed to %s, "
766: "id %d, off %d, len %d, interface %s, mtu %u: %s",
767: inet_ntoa (iph.ip_dst), iph.ip_id, iph.ip_off, iph.ip_len,
768: oi->ifp->name, oi->ifp->mtu, safe_strerror (errno));
769:
770: /* Show debug sending packet. */
771: if (IS_DEBUG_OSPF_PACKET (type - 1, SEND))
772: {
773: if (IS_DEBUG_OSPF_PACKET (type - 1, DETAIL))
774: {
775: zlog_debug ("-----------------------------------------------------");
776: ospf_ip_header_dump (&iph);
777: stream_set_getp (op->s, 0);
778: ospf_packet_dump (op->s);
779: }
780:
781: zlog_debug ("%s sent to [%s] via [%s].",
782: LOOKUP (ospf_packet_type_str, type), inet_ntoa (op->dst),
783: IF_NAME (oi));
784:
785: if (IS_DEBUG_OSPF_PACKET (type - 1, DETAIL))
786: zlog_debug ("-----------------------------------------------------");
787: }
788:
789: /* Now delete packet from queue. */
790: ospf_packet_delete (oi);
791:
792: if (ospf_fifo_head (oi->obuf) == NULL)
793: {
794: oi->on_write_q = 0;
795: list_delete_node (ospf->oi_write_q, node);
796: }
797:
798: /* If packets still remain in queue, call write thread. */
799: if (!list_isempty (ospf->oi_write_q))
800: ospf->t_write =
801: thread_add_write (master, ospf_write, ospf, ospf->fd);
802:
803: return 0;
804: }
805:
806: /* OSPF Hello message read -- RFC2328 Section 10.5. */
807: static void
808: ospf_hello (struct ip *iph, struct ospf_header *ospfh,
809: struct stream * s, struct ospf_interface *oi, int size)
810: {
811: struct ospf_hello *hello;
812: struct ospf_neighbor *nbr;
813: int old_state;
814: struct prefix p;
815:
816: /* increment statistics. */
817: oi->hello_in++;
818:
819: hello = (struct ospf_hello *) STREAM_PNT (s);
820:
821: /* If Hello is myself, silently discard. */
822: if (IPV4_ADDR_SAME (&ospfh->router_id, &oi->ospf->router_id))
823: {
824: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
825: {
826: zlog_debug ("ospf_header[%s/%s]: selforiginated, "
827: "dropping.",
828: LOOKUP (ospf_packet_type_str, ospfh->type),
829: inet_ntoa (iph->ip_src));
830: }
831: return;
832: }
833:
834: /* get neighbor prefix. */
835: p.family = AF_INET;
836: p.prefixlen = ip_masklen (hello->network_mask);
837: p.u.prefix4 = iph->ip_src;
838:
839: /* Compare network mask. */
840: /* Checking is ignored for Point-to-Point and Virtual link. */
841: if (oi->type != OSPF_IFTYPE_POINTOPOINT
842: && oi->type != OSPF_IFTYPE_VIRTUALLINK)
843: if (oi->address->prefixlen != p.prefixlen)
844: {
845: zlog_warn ("Packet %s [Hello:RECV]: NetworkMask mismatch on %s (configured prefix length is %d, but hello packet indicates %d).",
846: inet_ntoa(ospfh->router_id), IF_NAME(oi),
847: (int)oi->address->prefixlen, (int)p.prefixlen);
848: return;
849: }
850:
851: /* Compare Router Dead Interval. */
852: if (OSPF_IF_PARAM (oi, v_wait) != ntohl (hello->dead_interval))
853: {
854: zlog_warn ("Packet %s [Hello:RECV]: RouterDeadInterval mismatch "
855: "(expected %u, but received %u).",
856: inet_ntoa(ospfh->router_id),
857: OSPF_IF_PARAM(oi, v_wait), ntohl(hello->dead_interval));
858: return;
859: }
860:
861: /* Compare Hello Interval - ignored if fast-hellos are set. */
862: if (OSPF_IF_PARAM (oi, fast_hello) == 0)
863: {
864: if (OSPF_IF_PARAM (oi, v_hello) != ntohs (hello->hello_interval))
865: {
866: zlog_warn ("Packet %s [Hello:RECV]: HelloInterval mismatch "
867: "(expected %u, but received %u).",
868: inet_ntoa(ospfh->router_id),
869: OSPF_IF_PARAM(oi, v_hello), ntohs(hello->hello_interval));
870: return;
871: }
872: }
873:
874: if (IS_DEBUG_OSPF_EVENT)
875: zlog_debug ("Packet %s [Hello:RECV]: Options %s",
876: inet_ntoa (ospfh->router_id),
877: ospf_options_dump (hello->options));
878:
879: /* Compare options. */
880: #define REJECT_IF_TBIT_ON 1 /* XXX */
881: #ifdef REJECT_IF_TBIT_ON
882: if (CHECK_FLAG (hello->options, OSPF_OPTION_T))
883: {
884: /*
885: * This router does not support non-zero TOS.
886: * Drop this Hello packet not to establish neighbor relationship.
887: */
888: zlog_warn ("Packet %s [Hello:RECV]: T-bit on, drop it.",
889: inet_ntoa (ospfh->router_id));
890: return;
891: }
892: #endif /* REJECT_IF_TBIT_ON */
893:
894: #ifdef HAVE_OPAQUE_LSA
895: if (CHECK_FLAG (oi->ospf->config, OSPF_OPAQUE_CAPABLE)
896: && CHECK_FLAG (hello->options, OSPF_OPTION_O))
897: {
898: /*
899: * This router does know the correct usage of O-bit
900: * the bit should be set in DD packet only.
901: */
902: zlog_warn ("Packet %s [Hello:RECV]: O-bit abuse?",
903: inet_ntoa (ospfh->router_id));
904: #ifdef STRICT_OBIT_USAGE_CHECK
905: return; /* Reject this packet. */
906: #else /* STRICT_OBIT_USAGE_CHECK */
907: UNSET_FLAG (hello->options, OSPF_OPTION_O); /* Ignore O-bit. */
908: #endif /* STRICT_OBIT_USAGE_CHECK */
909: }
910: #endif /* HAVE_OPAQUE_LSA */
911:
912: /* new for NSSA is to ensure that NP is on and E is off */
913:
914: if (oi->area->external_routing == OSPF_AREA_NSSA)
915: {
916: if (! (CHECK_FLAG (OPTIONS (oi), OSPF_OPTION_NP)
917: && CHECK_FLAG (hello->options, OSPF_OPTION_NP)
918: && ! CHECK_FLAG (OPTIONS (oi), OSPF_OPTION_E)
919: && ! CHECK_FLAG (hello->options, OSPF_OPTION_E)))
920: {
921: zlog_warn ("NSSA-Packet-%s[Hello:RECV]: my options: %x, his options %x", inet_ntoa (ospfh->router_id), OPTIONS (oi), hello->options);
922: return;
923: }
924: if (IS_DEBUG_OSPF_NSSA)
925: zlog_debug ("NSSA-Hello:RECV:Packet from %s:", inet_ntoa(ospfh->router_id));
926: }
927: else
928: /* The setting of the E-bit found in the Hello Packet's Options
929: field must match this area's ExternalRoutingCapability A
930: mismatch causes processing to stop and the packet to be
931: dropped. The setting of the rest of the bits in the Hello
932: Packet's Options field should be ignored. */
933: if (CHECK_FLAG (OPTIONS (oi), OSPF_OPTION_E) !=
934: CHECK_FLAG (hello->options, OSPF_OPTION_E))
935: {
936: zlog_warn ("Packet %s [Hello:RECV]: my options: %x, his options %x",
937: inet_ntoa(ospfh->router_id), OPTIONS (oi), hello->options);
938: return;
939: }
940:
941: /* get neighbour struct */
942: nbr = ospf_nbr_get (oi, ospfh, iph, &p);
943:
944: /* neighbour must be valid, ospf_nbr_get creates if none existed */
945: assert (nbr);
946:
947: old_state = nbr->state;
948:
949: /* Add event to thread. */
950: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_PacketReceived);
951:
952: /* RFC2328 Section 9.5.1
953: If the router is not eligible to become Designated Router,
954: (snip) It must also send an Hello Packet in reply to an
955: Hello Packet received from any eligible neighbor (other than
956: the current Designated Router and Backup Designated Router). */
957: if (oi->type == OSPF_IFTYPE_NBMA)
958: if (PRIORITY(oi) == 0 && hello->priority > 0
959: && IPV4_ADDR_CMP(&DR(oi), &iph->ip_src)
960: && IPV4_ADDR_CMP(&BDR(oi), &iph->ip_src))
961: OSPF_NSM_TIMER_ON (nbr->t_hello_reply, ospf_hello_reply_timer,
962: OSPF_HELLO_REPLY_DELAY);
963:
964: /* on NBMA network type, it happens to receive bidirectional Hello packet
965: without advance 1-Way Received event.
966: To avoid incorrect DR-seletion, raise 1-Way Received event.*/
967: if (oi->type == OSPF_IFTYPE_NBMA &&
968: (old_state == NSM_Down || old_state == NSM_Attempt))
969: {
970: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_OneWayReceived);
971: nbr->priority = hello->priority;
972: nbr->d_router = hello->d_router;
973: nbr->bd_router = hello->bd_router;
974: return;
975: }
976:
977: if (ospf_nbr_bidirectional (&oi->ospf->router_id, hello->neighbors,
978: size - OSPF_HELLO_MIN_SIZE))
979: {
980: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_TwoWayReceived);
981: nbr->options |= hello->options;
982: }
983: else
984: {
985: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_OneWayReceived);
986: /* Set neighbor information. */
987: nbr->priority = hello->priority;
988: nbr->d_router = hello->d_router;
989: nbr->bd_router = hello->bd_router;
990: return;
991: }
992:
993: /* If neighbor itself declares DR and no BDR exists,
994: cause event BackupSeen */
995: if (IPV4_ADDR_SAME (&nbr->address.u.prefix4, &hello->d_router))
996: if (hello->bd_router.s_addr == 0 && oi->state == ISM_Waiting)
997: OSPF_ISM_EVENT_SCHEDULE (oi, ISM_BackupSeen);
998:
999: /* neighbor itself declares BDR. */
1000: if (oi->state == ISM_Waiting &&
1001: IPV4_ADDR_SAME (&nbr->address.u.prefix4, &hello->bd_router))
1002: OSPF_ISM_EVENT_SCHEDULE (oi, ISM_BackupSeen);
1003:
1004: /* had not previously. */
1005: if ((IPV4_ADDR_SAME (&nbr->address.u.prefix4, &hello->d_router) &&
1006: IPV4_ADDR_CMP (&nbr->address.u.prefix4, &nbr->d_router)) ||
1007: (IPV4_ADDR_CMP (&nbr->address.u.prefix4, &hello->d_router) &&
1008: IPV4_ADDR_SAME (&nbr->address.u.prefix4, &nbr->d_router)))
1009: OSPF_ISM_EVENT_SCHEDULE (oi, ISM_NeighborChange);
1010:
1011: /* had not previously. */
1012: if ((IPV4_ADDR_SAME (&nbr->address.u.prefix4, &hello->bd_router) &&
1013: IPV4_ADDR_CMP (&nbr->address.u.prefix4, &nbr->bd_router)) ||
1014: (IPV4_ADDR_CMP (&nbr->address.u.prefix4, &hello->bd_router) &&
1015: IPV4_ADDR_SAME (&nbr->address.u.prefix4, &nbr->bd_router)))
1016: OSPF_ISM_EVENT_SCHEDULE (oi, ISM_NeighborChange);
1017:
1018: /* Neighbor priority check. */
1019: if (nbr->priority >= 0 && nbr->priority != hello->priority)
1020: OSPF_ISM_EVENT_SCHEDULE (oi, ISM_NeighborChange);
1021:
1022: /* Set neighbor information. */
1023: nbr->priority = hello->priority;
1024: nbr->d_router = hello->d_router;
1025: nbr->bd_router = hello->bd_router;
1026: }
1027:
1028: /* Save DD flags/options/Seqnum received. */
1029: static void
1030: ospf_db_desc_save_current (struct ospf_neighbor *nbr,
1031: struct ospf_db_desc *dd)
1032: {
1033: nbr->last_recv.flags = dd->flags;
1034: nbr->last_recv.options = dd->options;
1035: nbr->last_recv.dd_seqnum = ntohl (dd->dd_seqnum);
1036: }
1037:
1038: /* Process rest of DD packet. */
1039: static void
1040: ospf_db_desc_proc (struct stream *s, struct ospf_interface *oi,
1041: struct ospf_neighbor *nbr, struct ospf_db_desc *dd,
1042: u_int16_t size)
1043: {
1044: struct ospf_lsa *new, *find;
1045: struct lsa_header *lsah;
1046:
1047: stream_forward_getp (s, OSPF_DB_DESC_MIN_SIZE);
1048: for (size -= OSPF_DB_DESC_MIN_SIZE;
1049: size >= OSPF_LSA_HEADER_SIZE; size -= OSPF_LSA_HEADER_SIZE)
1050: {
1051: lsah = (struct lsa_header *) STREAM_PNT (s);
1052: stream_forward_getp (s, OSPF_LSA_HEADER_SIZE);
1053:
1054: /* Unknown LS type. */
1055: if (lsah->type < OSPF_MIN_LSA || lsah->type >= OSPF_MAX_LSA)
1056: {
1057: zlog_warn ("Packet [DD:RECV]: Unknown LS type %d.", lsah->type);
1058: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1059: return;
1060: }
1061:
1062: #ifdef HAVE_OPAQUE_LSA
1063: if (IS_OPAQUE_LSA (lsah->type)
1064: && ! CHECK_FLAG (nbr->options, OSPF_OPTION_O))
1065: {
1066: zlog_warn ("LSA[Type%d:%s]: Opaque capability mismatch?", lsah->type, inet_ntoa (lsah->id));
1067: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1068: return;
1069: }
1070: #endif /* HAVE_OPAQUE_LSA */
1071:
1072: switch (lsah->type)
1073: {
1074: case OSPF_AS_EXTERNAL_LSA:
1075: #ifdef HAVE_OPAQUE_LSA
1076: case OSPF_OPAQUE_AS_LSA:
1077: #endif /* HAVE_OPAQUE_LSA */
1078: /* Check for stub area. Reject if AS-External from stub but
1079: allow if from NSSA. */
1080: if (oi->area->external_routing == OSPF_AREA_STUB)
1081: {
1082: zlog_warn ("Packet [DD:RECV]: LSA[Type%d:%s] from %s area.",
1083: lsah->type, inet_ntoa (lsah->id),
1084: (oi->area->external_routing == OSPF_AREA_STUB) ?\
1085: "STUB" : "NSSA");
1086: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1087: return;
1088: }
1089: break;
1090: default:
1091: break;
1092: }
1093:
1094: /* Create LS-request object. */
1095: new = ospf_ls_request_new (lsah);
1096:
1097: /* Lookup received LSA, then add LS request list. */
1098: find = ospf_lsa_lookup_by_header (oi->area, lsah);
1099:
1100: /* ospf_lsa_more_recent is fine with NULL pointers */
1101: switch (ospf_lsa_more_recent (find, new))
1102: {
1103: case -1:
1104: /* Neighbour has a more recent LSA, we must request it */
1105: ospf_ls_request_add (nbr, new);
1106: case 0:
1107: /* If we have a copy of this LSA, it's either less recent
1108: * and we're requesting it from neighbour (the case above), or
1109: * it's as recent and we both have same copy (this case).
1110: *
1111: * In neither of these two cases is there any point in
1112: * describing our copy of the LSA to the neighbour in a
1113: * DB-Summary packet, if we're still intending to do so.
1114: *
1115: * See: draft-ogier-ospf-dbex-opt-00.txt, describing the
1116: * backward compatible optimisation to OSPF DB Exchange /
1117: * DB Description process implemented here.
1118: */
1119: if (find)
1120: ospf_lsdb_delete (&nbr->db_sum, find);
1121: ospf_lsa_discard (new);
1122: break;
1123: default:
1124: /* We have the more recent copy, nothing specific to do:
1125: * - no need to request neighbours stale copy
1126: * - must leave DB summary list copy alone
1127: */
1128: if (IS_DEBUG_OSPF_EVENT)
1129: zlog_debug ("Packet [DD:RECV]: LSA received Type %d, "
1130: "ID %s is not recent.", lsah->type, inet_ntoa (lsah->id));
1131: ospf_lsa_discard (new);
1132: }
1133: }
1134:
1135: /* Master */
1136: if (IS_SET_DD_MS (nbr->dd_flags))
1137: {
1138: nbr->dd_seqnum++;
1139:
1140: /* Both sides have no More, then we're done with Exchange */
1141: if (!IS_SET_DD_M (dd->flags) && !IS_SET_DD_M (nbr->dd_flags))
1142: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_ExchangeDone);
1143: else
1144: ospf_db_desc_send (nbr);
1145: }
1146: /* Slave */
1147: else
1148: {
1149: nbr->dd_seqnum = ntohl (dd->dd_seqnum);
1150:
1151: /* Send DD packet in reply.
1152: *
1153: * Must be done to acknowledge the Master's DD, regardless of
1154: * whether we have more LSAs ourselves to describe.
1155: *
1156: * This function will clear the 'More' bit, if after this DD
1157: * we have no more LSAs to describe to the master..
1158: */
1159: ospf_db_desc_send (nbr);
1160:
1161: /* Slave can raise ExchangeDone now, if master is also done */
1162: if (!IS_SET_DD_M (dd->flags) && !IS_SET_DD_M (nbr->dd_flags))
1163: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_ExchangeDone);
1164: }
1165:
1166: /* Save received neighbor values from DD. */
1167: ospf_db_desc_save_current (nbr, dd);
1168: }
1169:
1170: static int
1171: ospf_db_desc_is_dup (struct ospf_db_desc *dd, struct ospf_neighbor *nbr)
1172: {
1173: /* Is DD duplicated? */
1174: if (dd->options == nbr->last_recv.options &&
1175: dd->flags == nbr->last_recv.flags &&
1176: dd->dd_seqnum == htonl (nbr->last_recv.dd_seqnum))
1177: return 1;
1178:
1179: return 0;
1180: }
1181:
1182: /* OSPF Database Description message read -- RFC2328 Section 10.6. */
1183: static void
1184: ospf_db_desc (struct ip *iph, struct ospf_header *ospfh,
1185: struct stream *s, struct ospf_interface *oi, u_int16_t size)
1186: {
1187: struct ospf_db_desc *dd;
1188: struct ospf_neighbor *nbr;
1189:
1190: /* Increment statistics. */
1191: oi->db_desc_in++;
1192:
1193: dd = (struct ospf_db_desc *) STREAM_PNT (s);
1194:
1195: nbr = ospf_nbr_lookup (oi, iph, ospfh);
1196: if (nbr == NULL)
1197: {
1198: zlog_warn ("Packet[DD]: Unknown Neighbor %s",
1199: inet_ntoa (ospfh->router_id));
1200: return;
1201: }
1202:
1203: /* Check MTU. */
1204: if ((OSPF_IF_PARAM (oi, mtu_ignore) == 0) &&
1205: (ntohs (dd->mtu) > oi->ifp->mtu))
1206: {
1207: zlog_warn ("Packet[DD]: Neighbor %s MTU %u is larger than [%s]'s MTU %u",
1208: inet_ntoa (nbr->router_id), ntohs (dd->mtu),
1209: IF_NAME (oi), oi->ifp->mtu);
1210: return;
1211: }
1212:
1213: /*
1214: * XXX HACK by Hasso Tepper. Setting N/P bit in NSSA area DD packets is not
1215: * required. In fact at least JunOS sends DD packets with P bit clear.
1216: * Until proper solution is developped, this hack should help.
1217: *
1218: * Update: According to the RFCs, N bit is specified /only/ for Hello
1219: * options, unfortunately its use in DD options is not specified. Hence some
1220: * implementations follow E-bit semantics and set it in DD options, and some
1221: * treat it as unspecified and hence follow the directive "default for
1222: * options is clear", ie unset.
1223: *
1224: * Reset the flag, as ospfd follows E-bit semantics.
1225: */
1226: if ( (oi->area->external_routing == OSPF_AREA_NSSA)
1227: && (CHECK_FLAG (nbr->options, OSPF_OPTION_NP))
1228: && (!CHECK_FLAG (dd->options, OSPF_OPTION_NP)) )
1229: {
1230: if (IS_DEBUG_OSPF_EVENT)
1231: zlog_debug ("Packet[DD]: Neighbour %s: Has NSSA capability, sends with N bit clear in DD options",
1232: inet_ntoa (nbr->router_id) );
1233: SET_FLAG (dd->options, OSPF_OPTION_NP);
1234: }
1235:
1236: #ifdef REJECT_IF_TBIT_ON
1237: if (CHECK_FLAG (dd->options, OSPF_OPTION_T))
1238: {
1239: /*
1240: * In Hello protocol, optional capability must have checked
1241: * to prevent this T-bit enabled router be my neighbor.
1242: */
1243: zlog_warn ("Packet[DD]: Neighbor %s: T-bit on?", inet_ntoa (nbr->router_id));
1244: return;
1245: }
1246: #endif /* REJECT_IF_TBIT_ON */
1247:
1248: #ifdef HAVE_OPAQUE_LSA
1249: if (CHECK_FLAG (dd->options, OSPF_OPTION_O)
1250: && !CHECK_FLAG (oi->ospf->config, OSPF_OPAQUE_CAPABLE))
1251: {
1252: /*
1253: * This node is not configured to handle O-bit, for now.
1254: * Clear it to ignore unsupported capability proposed by neighbor.
1255: */
1256: UNSET_FLAG (dd->options, OSPF_OPTION_O);
1257: }
1258: #endif /* HAVE_OPAQUE_LSA */
1259:
1260: /* Add event to thread. */
1261: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_PacketReceived);
1262:
1263: /* Process DD packet by neighbor status. */
1264: switch (nbr->state)
1265: {
1266: case NSM_Down:
1267: case NSM_Attempt:
1268: case NSM_TwoWay:
1269: zlog_warn ("Packet[DD]: Neighbor %s state is %s, packet discarded.",
1270: inet_ntoa(nbr->router_id),
1271: LOOKUP (ospf_nsm_state_msg, nbr->state));
1272: break;
1273: case NSM_Init:
1274: OSPF_NSM_EVENT_EXECUTE (nbr, NSM_TwoWayReceived);
1275: /* If the new state is ExStart, the processing of the current
1276: packet should then continue in this new state by falling
1277: through to case ExStart below. */
1278: if (nbr->state != NSM_ExStart)
1279: break;
1280: case NSM_ExStart:
1281: /* Initial DBD */
1282: if ((IS_SET_DD_ALL (dd->flags) == OSPF_DD_FLAG_ALL) &&
1283: (size == OSPF_DB_DESC_MIN_SIZE))
1284: {
1285: if (IPV4_ADDR_CMP (&nbr->router_id, &oi->ospf->router_id) > 0)
1286: {
1287: /* We're Slave---obey */
1288: zlog_info ("Packet[DD]: Neighbor %s Negotiation done (Slave).",
1289: inet_ntoa(nbr->router_id));
1290: nbr->dd_seqnum = ntohl (dd->dd_seqnum);
1291:
1292: /* Reset I/MS */
1293: UNSET_FLAG (nbr->dd_flags, (OSPF_DD_FLAG_MS|OSPF_DD_FLAG_I));
1294: }
1295: else
1296: {
1297: /* We're Master, ignore the initial DBD from Slave */
1298: zlog_info ("Packet[DD]: Neighbor %s: Initial DBD from Slave, "
1299: "ignoring.", inet_ntoa(nbr->router_id));
1300: break;
1301: }
1302: }
1303: /* Ack from the Slave */
1304: else if (!IS_SET_DD_MS (dd->flags) && !IS_SET_DD_I (dd->flags) &&
1305: ntohl (dd->dd_seqnum) == nbr->dd_seqnum &&
1306: IPV4_ADDR_CMP (&nbr->router_id, &oi->ospf->router_id) < 0)
1307: {
1308: zlog_info ("Packet[DD]: Neighbor %s Negotiation done (Master).",
1309: inet_ntoa(nbr->router_id));
1310: /* Reset I, leaving MS */
1311: UNSET_FLAG (nbr->dd_flags, OSPF_DD_FLAG_I);
1312: }
1313: else
1314: {
1315: zlog_warn ("Packet[DD]: Neighbor %s Negotiation fails.",
1316: inet_ntoa(nbr->router_id));
1317: break;
1318: }
1319:
1320: /* This is where the real Options are saved */
1321: nbr->options = dd->options;
1322:
1323: #ifdef HAVE_OPAQUE_LSA
1324: if (CHECK_FLAG (oi->ospf->config, OSPF_OPAQUE_CAPABLE))
1325: {
1326: if (IS_DEBUG_OSPF_EVENT)
1327: zlog_debug ("Neighbor[%s] is %sOpaque-capable.",
1328: inet_ntoa (nbr->router_id),
1329: CHECK_FLAG (nbr->options, OSPF_OPTION_O) ? "" : "NOT ");
1330:
1331: if (! CHECK_FLAG (nbr->options, OSPF_OPTION_O)
1332: && IPV4_ADDR_SAME (&DR (oi), &nbr->address.u.prefix4))
1333: {
1334: zlog_warn ("DR-neighbor[%s] is NOT opaque-capable; "
1335: "Opaque-LSAs cannot be reliably advertised "
1336: "in this network.",
1337: inet_ntoa (nbr->router_id));
1338: /* This situation is undesirable, but not a real error. */
1339: }
1340: }
1341: #endif /* HAVE_OPAQUE_LSA */
1342:
1343: OSPF_NSM_EVENT_EXECUTE (nbr, NSM_NegotiationDone);
1344:
1345: /* continue processing rest of packet. */
1346: ospf_db_desc_proc (s, oi, nbr, dd, size);
1347: break;
1348: case NSM_Exchange:
1349: if (ospf_db_desc_is_dup (dd, nbr))
1350: {
1351: if (IS_SET_DD_MS (nbr->dd_flags))
1352: /* Master: discard duplicated DD packet. */
1353: zlog_info ("Packet[DD] (Master): Neighbor %s packet duplicated.",
1354: inet_ntoa (nbr->router_id));
1355: else
1356: /* Slave: cause to retransmit the last Database Description. */
1357: {
1358: zlog_info ("Packet[DD] [Slave]: Neighbor %s packet duplicated.",
1359: inet_ntoa (nbr->router_id));
1360: ospf_db_desc_resend (nbr);
1361: }
1362: break;
1363: }
1364:
1365: /* Otherwise DD packet should be checked. */
1366: /* Check Master/Slave bit mismatch */
1367: if (IS_SET_DD_MS (dd->flags) != IS_SET_DD_MS (nbr->last_recv.flags))
1368: {
1369: zlog_warn ("Packet[DD]: Neighbor %s MS-bit mismatch.",
1370: inet_ntoa(nbr->router_id));
1371: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1372: if (IS_DEBUG_OSPF_EVENT)
1373: zlog_debug ("Packet[DD]: dd->flags=%d, nbr->dd_flags=%d",
1374: dd->flags, nbr->dd_flags);
1375: break;
1376: }
1377:
1378: /* Check initialize bit is set. */
1379: if (IS_SET_DD_I (dd->flags))
1380: {
1381: zlog_info ("Packet[DD]: Neighbor %s I-bit set.",
1382: inet_ntoa(nbr->router_id));
1383: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1384: break;
1385: }
1386:
1387: /* Check DD Options. */
1388: if (dd->options != nbr->options)
1389: {
1390: #ifdef ORIGINAL_CODING
1391: /* Save the new options for debugging */
1392: nbr->options = dd->options;
1393: #endif /* ORIGINAL_CODING */
1394: zlog_warn ("Packet[DD]: Neighbor %s options mismatch.",
1395: inet_ntoa(nbr->router_id));
1396: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1397: break;
1398: }
1399:
1400: /* Check DD sequence number. */
1401: if ((IS_SET_DD_MS (nbr->dd_flags) &&
1402: ntohl (dd->dd_seqnum) != nbr->dd_seqnum) ||
1403: (!IS_SET_DD_MS (nbr->dd_flags) &&
1404: ntohl (dd->dd_seqnum) != nbr->dd_seqnum + 1))
1405: {
1406: zlog_warn ("Packet[DD]: Neighbor %s sequence number mismatch.",
1407: inet_ntoa(nbr->router_id));
1408: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1409: break;
1410: }
1411:
1412: /* Continue processing rest of packet. */
1413: ospf_db_desc_proc (s, oi, nbr, dd, size);
1414: break;
1415: case NSM_Loading:
1416: case NSM_Full:
1417: if (ospf_db_desc_is_dup (dd, nbr))
1418: {
1419: if (IS_SET_DD_MS (nbr->dd_flags))
1420: {
1421: /* Master should discard duplicate DD packet. */
1422: zlog_info ("Packet[DD]: Neighbor %s duplicated, "
1423: "packet discarded.",
1424: inet_ntoa(nbr->router_id));
1425: break;
1426: }
1427: else
1428: {
1429: struct timeval t, now;
1430: quagga_gettime (QUAGGA_CLK_MONOTONIC, &now);
1431: t = tv_sub (now, nbr->last_send_ts);
1432: if (tv_cmp (t, int2tv (nbr->v_inactivity)) < 0)
1433: {
1434: /* In states Loading and Full the slave must resend
1435: its last Database Description packet in response to
1436: duplicate Database Description packets received
1437: from the master. For this reason the slave must
1438: wait RouterDeadInterval seconds before freeing the
1439: last Database Description packet. Reception of a
1440: Database Description packet from the master after
1441: this interval will generate a SeqNumberMismatch
1442: neighbor event. RFC2328 Section 10.8 */
1443: ospf_db_desc_resend (nbr);
1444: break;
1445: }
1446: }
1447: }
1448:
1449: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_SeqNumberMismatch);
1450: break;
1451: default:
1452: zlog_warn ("Packet[DD]: Neighbor %s NSM illegal status %u.",
1453: inet_ntoa(nbr->router_id), nbr->state);
1454: break;
1455: }
1456: }
1457:
1458: #define OSPF_LSA_KEY_SIZE 12 /* type(4) + id(4) + ar(4) */
1459:
1460: /* OSPF Link State Request Read -- RFC2328 Section 10.7. */
1461: static void
1462: ospf_ls_req (struct ip *iph, struct ospf_header *ospfh,
1463: struct stream *s, struct ospf_interface *oi, u_int16_t size)
1464: {
1465: struct ospf_neighbor *nbr;
1466: u_int32_t ls_type;
1467: struct in_addr ls_id;
1468: struct in_addr adv_router;
1469: struct ospf_lsa *find;
1470: struct list *ls_upd;
1471: unsigned int length;
1472:
1473: /* Increment statistics. */
1474: oi->ls_req_in++;
1475:
1476: nbr = ospf_nbr_lookup (oi, iph, ospfh);
1477: if (nbr == NULL)
1478: {
1479: zlog_warn ("Link State Request: Unknown Neighbor %s.",
1480: inet_ntoa (ospfh->router_id));
1481: return;
1482: }
1483:
1484: /* Add event to thread. */
1485: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_PacketReceived);
1486:
1487: /* Neighbor State should be Exchange or later. */
1488: if (nbr->state != NSM_Exchange &&
1489: nbr->state != NSM_Loading &&
1490: nbr->state != NSM_Full)
1491: {
1492: zlog_warn ("Link State Request received from %s: "
1493: "Neighbor state is %s, packet discarded.",
1494: inet_ntoa (ospfh->router_id),
1495: LOOKUP (ospf_nsm_state_msg, nbr->state));
1496: return;
1497: }
1498:
1499: /* Send Link State Update for ALL requested LSAs. */
1500: ls_upd = list_new ();
1501: length = OSPF_HEADER_SIZE + OSPF_LS_UPD_MIN_SIZE;
1502:
1503: while (size >= OSPF_LSA_KEY_SIZE)
1504: {
1505: /* Get one slice of Link State Request. */
1506: ls_type = stream_getl (s);
1507: ls_id.s_addr = stream_get_ipv4 (s);
1508: adv_router.s_addr = stream_get_ipv4 (s);
1509:
1510: /* Verify LSA type. */
1511: if (ls_type < OSPF_MIN_LSA || ls_type >= OSPF_MAX_LSA)
1512: {
1513: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_BadLSReq);
1514: list_delete (ls_upd);
1515: return;
1516: }
1517:
1518: /* Search proper LSA in LSDB. */
1519: find = ospf_lsa_lookup (oi->area, ls_type, ls_id, adv_router);
1520: if (find == NULL)
1521: {
1522: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_BadLSReq);
1523: list_delete (ls_upd);
1524: return;
1525: }
1526:
1527: /* Packet overflows MTU size, send immediately. */
1528: if (length + ntohs (find->data->length) > ospf_packet_max (oi))
1529: {
1530: if (oi->type == OSPF_IFTYPE_NBMA)
1531: ospf_ls_upd_send (nbr, ls_upd, OSPF_SEND_PACKET_DIRECT);
1532: else
1533: ospf_ls_upd_send (nbr, ls_upd, OSPF_SEND_PACKET_INDIRECT);
1534:
1535: /* Only remove list contents. Keep ls_upd. */
1536: list_delete_all_node (ls_upd);
1537:
1538: length = OSPF_HEADER_SIZE + OSPF_LS_UPD_MIN_SIZE;
1539: }
1540:
1541: /* Append LSA to update list. */
1542: listnode_add (ls_upd, find);
1543: length += ntohs (find->data->length);
1544:
1545: size -= OSPF_LSA_KEY_SIZE;
1546: }
1547:
1548: /* Send rest of Link State Update. */
1549: if (listcount (ls_upd) > 0)
1550: {
1551: if (oi->type == OSPF_IFTYPE_NBMA)
1552: ospf_ls_upd_send (nbr, ls_upd, OSPF_SEND_PACKET_DIRECT);
1553: else
1554: ospf_ls_upd_send (nbr, ls_upd, OSPF_SEND_PACKET_INDIRECT);
1555:
1556: list_delete (ls_upd);
1557: }
1558: else
1559: list_free (ls_upd);
1560: }
1561:
1562: /* Get the list of LSAs from Link State Update packet.
1563: And process some validation -- RFC2328 Section 13. (1)-(2). */
1564: static struct list *
1565: ospf_ls_upd_list_lsa (struct ospf_neighbor *nbr, struct stream *s,
1566: struct ospf_interface *oi, size_t size)
1567: {
1568: u_int16_t count, sum;
1569: u_int32_t length;
1570: struct lsa_header *lsah;
1571: struct ospf_lsa *lsa;
1572: struct list *lsas;
1573:
1574: lsas = list_new ();
1575:
1576: count = stream_getl (s);
1577: size -= OSPF_LS_UPD_MIN_SIZE; /* # LSAs */
1578:
1579: for (; size >= OSPF_LSA_HEADER_SIZE && count > 0;
1580: size -= length, stream_forward_getp (s, length), count--)
1581: {
1582: lsah = (struct lsa_header *) STREAM_PNT (s);
1583: length = ntohs (lsah->length);
1584:
1585: if (length > size)
1586: {
1587: zlog_warn ("Link State Update: LSA length exceeds packet size.");
1588: break;
1589: }
1590:
1591: /* Validate the LSA's LS checksum. */
1592: sum = lsah->checksum;
1593: if (sum != ospf_lsa_checksum (lsah))
1594: {
1595: zlog_warn ("Link State Update: LSA checksum error %x, %x.",
1596: sum, lsah->checksum);
1597: continue;
1598: }
1599:
1600: /* Examine the LSA's LS type. */
1601: if (lsah->type < OSPF_MIN_LSA || lsah->type >= OSPF_MAX_LSA)
1602: {
1603: zlog_warn ("Link State Update: Unknown LS type %d", lsah->type);
1604: continue;
1605: }
1606:
1607: /*
1608: * What if the received LSA's age is greater than MaxAge?
1609: * Treat it as a MaxAge case -- endo.
1610: */
1611: if (ntohs (lsah->ls_age) > OSPF_LSA_MAXAGE)
1612: lsah->ls_age = htons (OSPF_LSA_MAXAGE);
1613:
1614: #ifdef HAVE_OPAQUE_LSA
1615: if (CHECK_FLAG (nbr->options, OSPF_OPTION_O))
1616: {
1617: #ifdef STRICT_OBIT_USAGE_CHECK
1618: if ((IS_OPAQUE_LSA(lsah->type) &&
1619: ! CHECK_FLAG (lsah->options, OSPF_OPTION_O))
1620: || (! IS_OPAQUE_LSA(lsah->type) &&
1621: CHECK_FLAG (lsah->options, OSPF_OPTION_O)))
1622: {
1623: /*
1624: * This neighbor must know the exact usage of O-bit;
1625: * the bit will be set in Type-9,10,11 LSAs only.
1626: */
1627: zlog_warn ("LSA[Type%d:%s]: O-bit abuse?", lsah->type, inet_ntoa (lsah->id));
1628: continue;
1629: }
1630: #endif /* STRICT_OBIT_USAGE_CHECK */
1631:
1632: /* Do not take in AS External Opaque-LSAs if we are a stub. */
1633: if (lsah->type == OSPF_OPAQUE_AS_LSA
1634: && nbr->oi->area->external_routing != OSPF_AREA_DEFAULT)
1635: {
1636: if (IS_DEBUG_OSPF_EVENT)
1637: zlog_debug ("LSA[Type%d:%s]: We are a stub, don't take this LSA.", lsah->type, inet_ntoa (lsah->id));
1638: continue;
1639: }
1640: }
1641: else if (IS_OPAQUE_LSA(lsah->type))
1642: {
1643: zlog_warn ("LSA[Type%d:%s]: Opaque capability mismatch?", lsah->type, inet_ntoa (lsah->id));
1644: continue;
1645: }
1646: #endif /* HAVE_OPAQUE_LSA */
1647:
1648: /* Create OSPF LSA instance. */
1649: lsa = ospf_lsa_new ();
1650:
1651: /* We may wish to put some error checking if type NSSA comes in
1652: and area not in NSSA mode */
1653: switch (lsah->type)
1654: {
1655: case OSPF_AS_EXTERNAL_LSA:
1656: #ifdef HAVE_OPAQUE_LSA
1657: case OSPF_OPAQUE_AS_LSA:
1658: lsa->area = NULL;
1659: break;
1660: case OSPF_OPAQUE_LINK_LSA:
1661: lsa->oi = oi; /* Remember incoming interface for flooding control. */
1662: /* Fallthrough */
1663: #endif /* HAVE_OPAQUE_LSA */
1664: default:
1665: lsa->area = oi->area;
1666: break;
1667: }
1668:
1669: lsa->data = ospf_lsa_data_new (length);
1670: memcpy (lsa->data, lsah, length);
1671:
1672: if (IS_DEBUG_OSPF_EVENT)
1673: zlog_debug("LSA[Type%d:%s]: %p new LSA created with Link State Update",
1674: lsa->data->type, inet_ntoa (lsa->data->id), lsa);
1675: listnode_add (lsas, lsa);
1676: }
1677:
1678: return lsas;
1679: }
1680:
1681: /* Cleanup Update list. */
1682: static void
1683: ospf_upd_list_clean (struct list *lsas)
1684: {
1685: struct listnode *node, *nnode;
1686: struct ospf_lsa *lsa;
1687:
1688: for (ALL_LIST_ELEMENTS (lsas, node, nnode, lsa))
1689: ospf_lsa_discard (lsa);
1690:
1691: list_delete (lsas);
1692: }
1693:
1694: /* OSPF Link State Update message read -- RFC2328 Section 13. */
1695: static void
1696: ospf_ls_upd (struct ip *iph, struct ospf_header *ospfh,
1697: struct stream *s, struct ospf_interface *oi, u_int16_t size)
1698: {
1699: struct ospf_neighbor *nbr;
1700: struct list *lsas;
1701: struct listnode *node, *nnode;
1702: struct ospf_lsa *lsa = NULL;
1703: /* unsigned long ls_req_found = 0; */
1704:
1705: /* Dis-assemble the stream, update each entry, re-encapsulate for flooding */
1706:
1707: /* Increment statistics. */
1708: oi->ls_upd_in++;
1709:
1710: /* Check neighbor. */
1711: nbr = ospf_nbr_lookup (oi, iph, ospfh);
1712: if (nbr == NULL)
1713: {
1714: zlog_warn ("Link State Update: Unknown Neighbor %s on int: %s",
1715: inet_ntoa (ospfh->router_id), IF_NAME (oi));
1716: return;
1717: }
1718:
1719: /* Add event to thread. */
1720: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_PacketReceived);
1721:
1722: /* Check neighbor state. */
1723: if (nbr->state < NSM_Exchange)
1724: {
1725: zlog_warn ("Link State Update: "
1726: "Neighbor[%s] state %s is less than Exchange",
1727: inet_ntoa (ospfh->router_id),
1728: LOOKUP(ospf_nsm_state_msg, nbr->state));
1729: return;
1730: }
1731:
1732: /* Get list of LSAs from Link State Update packet. - Also perorms Stages
1733: * 1 (validate LSA checksum) and 2 (check for LSA consistent type)
1734: * of section 13.
1735: */
1736: lsas = ospf_ls_upd_list_lsa (nbr, s, oi, size);
1737:
1738: #ifdef HAVE_OPAQUE_LSA
1739: /*
1740: * If self-originated Opaque-LSAs that have flooded before restart
1741: * are contained in the received LSUpd message, corresponding LSReq
1742: * messages to be sent may have to be modified.
1743: * To eliminate possible race conditions such that flushing and normal
1744: * updating for the same LSA would take place alternately, this trick
1745: * must be done before entering to the loop below.
1746: */
1747: /* XXX: Why is this Opaque specific? Either our core code is deficient
1748: * and this should be fixed generally, or Opaque is inventing strawman
1749: * problems */
1750: ospf_opaque_adjust_lsreq (nbr, lsas);
1751: #endif /* HAVE_OPAQUE_LSA */
1752:
1753: #define DISCARD_LSA(L,N) {\
1754: if (IS_DEBUG_OSPF_EVENT) \
1755: zlog_debug ("ospf_lsa_discard() in ospf_ls_upd() point %d: lsa %p Type-%d", N, lsa, (int) lsa->data->type); \
1756: ospf_lsa_discard (L); \
1757: continue; }
1758:
1759: /* Process each LSA received in the one packet. */
1760: for (ALL_LIST_ELEMENTS (lsas, node, nnode, lsa))
1761: {
1762: struct ospf_lsa *ls_ret, *current;
1763: int ret = 1;
1764:
1765: if (IS_DEBUG_OSPF_NSSA)
1766: {
1767: char buf1[INET_ADDRSTRLEN];
1768: char buf2[INET_ADDRSTRLEN];
1769: char buf3[INET_ADDRSTRLEN];
1770:
1771: zlog_debug("LSA Type-%d from %s, ID: %s, ADV: %s",
1772: lsa->data->type,
1773: inet_ntop (AF_INET, &ospfh->router_id,
1774: buf1, INET_ADDRSTRLEN),
1775: inet_ntop (AF_INET, &lsa->data->id,
1776: buf2, INET_ADDRSTRLEN),
1777: inet_ntop (AF_INET, &lsa->data->adv_router,
1778: buf3, INET_ADDRSTRLEN));
1779: }
1780:
1781: listnode_delete (lsas, lsa); /* We don't need it in list anymore */
1782:
1783: /* Validate Checksum - Done above by ospf_ls_upd_list_lsa() */
1784:
1785: /* LSA Type - Done above by ospf_ls_upd_list_lsa() */
1786:
1787: /* Do not take in AS External LSAs if we are a stub or NSSA. */
1788:
1789: /* Do not take in AS NSSA if this neighbor and we are not NSSA */
1790:
1791: /* Do take in Type-7's if we are an NSSA */
1792:
1793: /* If we are also an ABR, later translate them to a Type-5 packet */
1794:
1795: /* Later, an NSSA Re-fresh can Re-fresh Type-7's and an ABR will
1796: translate them to a separate Type-5 packet. */
1797:
1798: if (lsa->data->type == OSPF_AS_EXTERNAL_LSA)
1799: /* Reject from STUB or NSSA */
1800: if (nbr->oi->area->external_routing != OSPF_AREA_DEFAULT)
1801: {
1802: if (IS_DEBUG_OSPF_NSSA)
1803: zlog_debug("Incoming External LSA Discarded: We are NSSA/STUB Area");
1804: DISCARD_LSA (lsa, 1);
1805: }
1806:
1807: if (lsa->data->type == OSPF_AS_NSSA_LSA)
1808: if (nbr->oi->area->external_routing != OSPF_AREA_NSSA)
1809: {
1810: if (IS_DEBUG_OSPF_NSSA)
1811: zlog_debug("Incoming NSSA LSA Discarded: Not NSSA Area");
1812: DISCARD_LSA (lsa,2);
1813: }
1814:
1815: /* Find the LSA in the current database. */
1816:
1817: current = ospf_lsa_lookup_by_header (oi->area, lsa->data);
1818:
1819: /* If the LSA's LS age is equal to MaxAge, and there is currently
1820: no instance of the LSA in the router's link state database,
1821: and none of router's neighbors are in states Exchange or Loading,
1822: then take the following actions. */
1823:
1824: if (IS_LSA_MAXAGE (lsa) && !current &&
1825: (ospf_nbr_count (oi, NSM_Exchange) +
1826: ospf_nbr_count (oi, NSM_Loading)) == 0)
1827: {
1828: /* Response Link State Acknowledgment. */
1829: ospf_ls_ack_send (nbr, lsa);
1830:
1831: /* Discard LSA. */
1832: zlog_info ("Link State Update[%s]: LS age is equal to MaxAge.",
1833: dump_lsa_key(lsa));
1834: DISCARD_LSA (lsa, 3);
1835: }
1836:
1837: #ifdef HAVE_OPAQUE_LSA
1838: if (IS_OPAQUE_LSA (lsa->data->type)
1839: && IPV4_ADDR_SAME (&lsa->data->adv_router, &oi->ospf->router_id))
1840: {
1841: /*
1842: * Even if initial flushing seems to be completed, there might
1843: * be a case that self-originated LSA with MaxAge still remain
1844: * in the routing domain.
1845: * Just send an LSAck message to cease retransmission.
1846: */
1847: if (IS_LSA_MAXAGE (lsa))
1848: {
1849: zlog_warn ("LSA[%s]: Boomerang effect?", dump_lsa_key (lsa));
1850: ospf_ls_ack_send (nbr, lsa);
1851: ospf_lsa_discard (lsa);
1852:
1853: if (current != NULL && ! IS_LSA_MAXAGE (current))
1854: ospf_opaque_lsa_refresh_schedule (current);
1855: continue;
1856: }
1857:
1858: /*
1859: * If an instance of self-originated Opaque-LSA is not found
1860: * in the LSDB, there are some possible cases here.
1861: *
1862: * 1) This node lost opaque-capability after restart.
1863: * 2) Else, a part of opaque-type is no more supported.
1864: * 3) Else, a part of opaque-id is no more supported.
1865: *
1866: * Anyway, it is still this node's responsibility to flush it.
1867: * Otherwise, the LSA instance remains in the routing domain
1868: * until its age reaches to MaxAge.
1869: */
1870: /* XXX: We should deal with this for *ALL* LSAs, not just opaque */
1871: if (current == NULL)
1872: {
1873: if (IS_DEBUG_OSPF_EVENT)
1874: zlog_debug ("LSA[%s]: Previously originated Opaque-LSA,"
1875: "not found in the LSDB.", dump_lsa_key (lsa));
1876:
1877: SET_FLAG (lsa->flags, OSPF_LSA_SELF);
1878:
1879: ospf_opaque_self_originated_lsa_received (nbr, lsa);
1880: ospf_ls_ack_send (nbr, lsa);
1881:
1882: continue;
1883: }
1884: }
1885: #endif /* HAVE_OPAQUE_LSA */
1886:
1887: /* It might be happen that received LSA is self-originated network LSA, but
1888: * router ID is cahnged. So, we should check if LSA is a network-LSA whose
1889: * Link State ID is one of the router's own IP interface addresses but whose
1890: * Advertising Router is not equal to the router's own Router ID
1891: * According to RFC 2328 12.4.2 and 13.4 this LSA should be flushed.
1892: */
1893:
1894: if(lsa->data->type == OSPF_NETWORK_LSA)
1895: {
1896: struct listnode *oinode, *oinnode;
1897: struct ospf_interface *out_if;
1898: int Flag = 0;
1899:
1900: for (ALL_LIST_ELEMENTS (oi->ospf->oiflist, oinode, oinnode, out_if))
1901: {
1902: if(out_if == NULL)
1903: break;
1904:
1905: if((IPV4_ADDR_SAME(&out_if->address->u.prefix4, &lsa->data->id)) &&
1906: (!(IPV4_ADDR_SAME(&oi->ospf->router_id, &lsa->data->adv_router))))
1907: {
1908: if(out_if->network_lsa_self)
1909: {
1910: ospf_lsa_flush_area(lsa,out_if->area);
1911: if(IS_DEBUG_OSPF_EVENT)
1912: zlog_debug ("ospf_lsa_discard() in ospf_ls_upd() point 9: lsa %p Type-%d",
1913: lsa, (int) lsa->data->type);
1914: ospf_lsa_discard (lsa);
1915: Flag = 1;
1916: }
1917: break;
1918: }
1919: }
1920: if(Flag)
1921: continue;
1922: }
1923:
1924: /* (5) Find the instance of this LSA that is currently contained
1925: in the router's link state database. If there is no
1926: database copy, or the received LSA is more recent than
1927: the database copy the following steps must be performed. */
1928:
1929: if (current == NULL ||
1930: (ret = ospf_lsa_more_recent (current, lsa)) < 0)
1931: {
1932: /* Actual flooding procedure. */
1933: if (ospf_flood (oi->ospf, nbr, current, lsa) < 0) /* Trap NSSA later. */
1934: DISCARD_LSA (lsa, 4);
1935: continue;
1936: }
1937:
1938: /* (6) Else, If there is an instance of the LSA on the sending
1939: neighbor's Link state request list, an error has occurred in
1940: the Database Exchange process. In this case, restart the
1941: Database Exchange process by generating the neighbor event
1942: BadLSReq for the sending neighbor and stop processing the
1943: Link State Update packet. */
1944:
1945: if (ospf_ls_request_lookup (nbr, lsa))
1946: {
1947: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_BadLSReq);
1948: zlog_warn("LSA[%s] instance exists on Link state request list",
1949: dump_lsa_key(lsa));
1950:
1951: /* Clean list of LSAs. */
1952: ospf_upd_list_clean (lsas);
1953: /* this lsa is not on lsas list already. */
1954: ospf_lsa_discard (lsa);
1955: return;
1956: }
1957:
1958: /* If the received LSA is the same instance as the database copy
1959: (i.e., neither one is more recent) the following two steps
1960: should be performed: */
1961:
1962: if (ret == 0)
1963: {
1964: /* If the LSA is listed in the Link state retransmission list
1965: for the receiving adjacency, the router itself is expecting
1966: an acknowledgment for this LSA. The router should treat the
1967: received LSA as an acknowledgment by removing the LSA from
1968: the Link state retransmission list. This is termed an
1969: "implied acknowledgment". */
1970:
1971: ls_ret = ospf_ls_retransmit_lookup (nbr, lsa);
1972:
1973: if (ls_ret != NULL)
1974: {
1975: ospf_ls_retransmit_delete (nbr, ls_ret);
1976:
1977: /* Delayed acknowledgment sent if advertisement received
1978: from Designated Router, otherwise do nothing. */
1979: if (oi->state == ISM_Backup)
1980: if (NBR_IS_DR (nbr))
1981: listnode_add (oi->ls_ack, ospf_lsa_lock (lsa));
1982:
1983: DISCARD_LSA (lsa, 5);
1984: }
1985: else
1986: /* Acknowledge the receipt of the LSA by sending a
1987: Link State Acknowledgment packet back out the receiving
1988: interface. */
1989: {
1990: ospf_ls_ack_send (nbr, lsa);
1991: DISCARD_LSA (lsa, 6);
1992: }
1993: }
1994:
1995: /* The database copy is more recent. If the database copy
1996: has LS age equal to MaxAge and LS sequence number equal to
1997: MaxSequenceNumber, simply discard the received LSA without
1998: acknowledging it. (In this case, the LSA's LS sequence number is
1999: wrapping, and the MaxSequenceNumber LSA must be completely
2000: flushed before any new LSA instance can be introduced). */
2001:
2002: else if (ret > 0) /* Database copy is more recent */
2003: {
2004: if (IS_LSA_MAXAGE (current) &&
2005: current->data->ls_seqnum == htonl (OSPF_MAX_SEQUENCE_NUMBER))
2006: {
2007: DISCARD_LSA (lsa, 7);
2008: }
2009: /* Otherwise, as long as the database copy has not been sent in a
2010: Link State Update within the last MinLSArrival seconds, send the
2011: database copy back to the sending neighbor, encapsulated within
2012: a Link State Update Packet. The Link State Update Packet should
2013: be sent directly to the neighbor. In so doing, do not put the
2014: database copy of the LSA on the neighbor's link state
2015: retransmission list, and do not acknowledge the received (less
2016: recent) LSA instance. */
2017: else
2018: {
2019: struct timeval now;
2020:
2021: quagga_gettime (QUAGGA_CLK_MONOTONIC, &now);
2022:
2023: if (tv_cmp (tv_sub (now, current->tv_orig),
2024: int2tv (OSPF_MIN_LS_ARRIVAL)) >= 0)
2025: /* Trap NSSA type later.*/
2026: ospf_ls_upd_send_lsa (nbr, current, OSPF_SEND_PACKET_DIRECT);
2027: DISCARD_LSA (lsa, 8);
2028: }
2029: }
2030: }
2031: #undef DISCARD_LSA
2032:
2033: assert (listcount (lsas) == 0);
2034: list_delete (lsas);
2035: }
2036:
2037: /* OSPF Link State Acknowledgment message read -- RFC2328 Section 13.7. */
2038: static void
2039: ospf_ls_ack (struct ip *iph, struct ospf_header *ospfh,
2040: struct stream *s, struct ospf_interface *oi, u_int16_t size)
2041: {
2042: struct ospf_neighbor *nbr;
2043:
2044: /* increment statistics. */
2045: oi->ls_ack_in++;
2046:
2047: nbr = ospf_nbr_lookup (oi, iph, ospfh);
2048: if (nbr == NULL)
2049: {
2050: zlog_warn ("Link State Acknowledgment: Unknown Neighbor %s.",
2051: inet_ntoa (ospfh->router_id));
2052: return;
2053: }
2054:
2055: /* Add event to thread. */
2056: OSPF_NSM_EVENT_SCHEDULE (nbr, NSM_PacketReceived);
2057:
2058: if (nbr->state < NSM_Exchange)
2059: {
2060: zlog_warn ("Link State Acknowledgment: "
2061: "Neighbor[%s] state %s is less than Exchange",
2062: inet_ntoa (ospfh->router_id),
2063: LOOKUP(ospf_nsm_state_msg, nbr->state));
2064: return;
2065: }
2066:
2067: while (size >= OSPF_LSA_HEADER_SIZE)
2068: {
2069: struct ospf_lsa *lsa, *lsr;
2070:
2071: lsa = ospf_lsa_new ();
2072: lsa->data = (struct lsa_header *) STREAM_PNT (s);
2073:
2074: /* lsah = (struct lsa_header *) STREAM_PNT (s); */
2075: size -= OSPF_LSA_HEADER_SIZE;
2076: stream_forward_getp (s, OSPF_LSA_HEADER_SIZE);
2077:
2078: if (lsa->data->type < OSPF_MIN_LSA || lsa->data->type >= OSPF_MAX_LSA)
2079: {
2080: lsa->data = NULL;
2081: ospf_lsa_discard (lsa);
2082: continue;
2083: }
2084:
2085: lsr = ospf_ls_retransmit_lookup (nbr, lsa);
2086:
2087: if (lsr != NULL && lsr->data->ls_seqnum == lsa->data->ls_seqnum)
2088: {
2089: #ifdef HAVE_OPAQUE_LSA
2090: if (IS_OPAQUE_LSA (lsr->data->type))
2091: ospf_opaque_ls_ack_received (nbr, lsr);
2092: #endif /* HAVE_OPAQUE_LSA */
2093:
2094: ospf_ls_retransmit_delete (nbr, lsr);
2095: }
2096:
2097: lsa->data = NULL;
2098: ospf_lsa_discard (lsa);
2099: }
2100:
2101: return;
2102: }
2103:
2104: static struct stream *
2105: ospf_recv_packet (int fd, struct interface **ifp, struct stream *ibuf)
2106: {
2107: int ret;
2108: struct ip *iph;
2109: u_int16_t ip_len;
2110: unsigned int ifindex = 0;
2111: struct iovec iov;
2112: /* Header and data both require alignment. */
2113: char buff [CMSG_SPACE(SOPT_SIZE_CMSG_IFINDEX_IPV4())];
2114: struct msghdr msgh;
2115:
2116: memset (&msgh, 0, sizeof (struct msghdr));
2117: msgh.msg_iov = &iov;
2118: msgh.msg_iovlen = 1;
2119: msgh.msg_control = (caddr_t) buff;
2120: msgh.msg_controllen = sizeof (buff);
2121:
2122: ret = stream_recvmsg (ibuf, fd, &msgh, 0, OSPF_MAX_PACKET_SIZE+1);
2123: if (ret < 0)
2124: {
2125: zlog_warn("stream_recvmsg failed: %s", safe_strerror(errno));
2126: return NULL;
2127: }
2128: if ((unsigned int)ret < sizeof(iph)) /* ret must be > 0 now */
2129: {
2130: zlog_warn("ospf_recv_packet: discarding runt packet of length %d "
2131: "(ip header size is %u)",
2132: ret, (u_int)sizeof(iph));
2133: return NULL;
2134: }
2135:
2136: /* Note that there should not be alignment problems with this assignment
2137: because this is at the beginning of the stream data buffer. */
2138: iph = (struct ip *) STREAM_DATA(ibuf);
2139: sockopt_iphdrincl_swab_systoh (iph);
2140:
2141: ip_len = iph->ip_len;
2142:
2143: #if !defined(GNU_LINUX) && (OpenBSD < 200311)
2144: /*
2145: * Kernel network code touches incoming IP header parameters,
2146: * before protocol specific processing.
2147: *
2148: * 1) Convert byteorder to host representation.
2149: * --> ip_len, ip_id, ip_off
2150: *
2151: * 2) Adjust ip_len to strip IP header size!
2152: * --> If user process receives entire IP packet via RAW
2153: * socket, it must consider adding IP header size to
2154: * the "ip_len" field of "ip" structure.
2155: *
2156: * For more details, see <netinet/ip_input.c>.
2157: */
2158: ip_len = ip_len + (iph->ip_hl << 2);
2159: #endif
2160:
2161: #if defined(__DragonFly__)
2162: /*
2163: * in DragonFly's raw socket, ip_len/ip_off are read
2164: * in network byte order.
2165: * As OpenBSD < 200311 adjust ip_len to strip IP header size!
2166: */
2167: ip_len = ntohs(iph->ip_len) + (iph->ip_hl << 2);
2168: #endif
2169:
2170: ifindex = getsockopt_ifindex (AF_INET, &msgh);
2171:
2172: *ifp = if_lookup_by_index (ifindex);
2173:
2174: if (ret != ip_len)
2175: {
2176: zlog_warn ("ospf_recv_packet read length mismatch: ip_len is %d, "
2177: "but recvmsg returned %d", ip_len, ret);
2178: return NULL;
2179: }
2180:
2181: return ibuf;
2182: }
2183:
2184: static struct ospf_interface *
2185: ospf_associate_packet_vl (struct ospf *ospf, struct interface *ifp,
2186: struct ip *iph, struct ospf_header *ospfh)
2187: {
2188: struct ospf_interface *rcv_oi;
2189: struct ospf_vl_data *vl_data;
2190: struct ospf_area *vl_area;
2191: struct listnode *node;
2192:
2193: if (IN_MULTICAST (ntohl (iph->ip_dst.s_addr)) ||
2194: !OSPF_IS_AREA_BACKBONE (ospfh))
2195: return NULL;
2196:
2197: /* look for local OSPF interface matching the destination
2198: * to determine Area ID. We presume therefore the destination address
2199: * is unique, or at least (for "unnumbered" links), not used in other
2200: * areas
2201: */
2202: if ((rcv_oi = ospf_if_lookup_by_local_addr (ospf, NULL,
2203: iph->ip_dst)) == NULL)
2204: return NULL;
2205:
2206: for (ALL_LIST_ELEMENTS_RO (ospf->vlinks, node, vl_data))
2207: {
2208: vl_area = ospf_area_lookup_by_area_id (ospf, vl_data->vl_area_id);
2209: if (!vl_area)
2210: continue;
2211:
2212: if (OSPF_AREA_SAME (&vl_area, &rcv_oi->area) &&
2213: IPV4_ADDR_SAME (&vl_data->vl_peer, &ospfh->router_id))
2214: {
2215: if (IS_DEBUG_OSPF_EVENT)
2216: zlog_debug ("associating packet with %s",
2217: IF_NAME (vl_data->vl_oi));
2218: if (! CHECK_FLAG (vl_data->vl_oi->ifp->flags, IFF_UP))
2219: {
2220: if (IS_DEBUG_OSPF_EVENT)
2221: zlog_debug ("This VL is not up yet, sorry");
2222: return NULL;
2223: }
2224:
2225: return vl_data->vl_oi;
2226: }
2227: }
2228:
2229: if (IS_DEBUG_OSPF_EVENT)
2230: zlog_debug ("couldn't find any VL to associate the packet with");
2231:
2232: return NULL;
2233: }
2234:
2235: static inline int
2236: ospf_check_area_id (struct ospf_interface *oi, struct ospf_header *ospfh)
2237: {
2238: /* Check match the Area ID of the receiving interface. */
2239: if (OSPF_AREA_SAME (&oi->area, &ospfh))
2240: return 1;
2241:
2242: return 0;
2243: }
2244:
2245: /* Unbound socket will accept any Raw IP packets if proto is matched.
2246: To prevent it, compare src IP address and i/f address with masking
2247: i/f network mask. */
2248: static int
2249: ospf_check_network_mask (struct ospf_interface *oi, struct in_addr ip_src)
2250: {
2251: struct in_addr mask, me, him;
2252:
2253: if (oi->type == OSPF_IFTYPE_POINTOPOINT ||
2254: oi->type == OSPF_IFTYPE_VIRTUALLINK)
2255: return 1;
2256:
2257: masklen2ip (oi->address->prefixlen, &mask);
2258:
2259: me.s_addr = oi->address->u.prefix4.s_addr & mask.s_addr;
2260: him.s_addr = ip_src.s_addr & mask.s_addr;
2261:
2262: if (IPV4_ADDR_SAME (&me, &him))
2263: return 1;
2264:
2265: return 0;
2266: }
2267:
2268: /* Return 1, if the packet is properly authenticated and checksummed,
2269: 0 otherwise. In particular, check that AuType header field is valid and
2270: matches the locally configured AuType, and that D.5 requirements are met. */
2271: static int
2272: ospf_check_auth (struct ospf_interface *oi, struct ospf_header *ospfh)
2273: {
2274: struct crypt_key *ck;
2275: u_int16_t iface_auth_type;
2276: u_int16_t pkt_auth_type = ntohs (ospfh->auth_type);
2277:
2278: switch (pkt_auth_type)
2279: {
2280: case OSPF_AUTH_NULL: /* RFC2328 D.5.1 */
2281: if (OSPF_AUTH_NULL != (iface_auth_type = ospf_auth_type (oi)))
2282: {
2283: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2284: zlog_warn ("interface %s: auth-type mismatch, local %s, rcvd Null",
2285: IF_NAME (oi), LOOKUP (ospf_auth_type_str, iface_auth_type));
2286: return 0;
2287: }
2288: if (! ospf_check_sum (ospfh))
2289: {
2290: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2291: zlog_warn ("interface %s: Null auth OK, but checksum error, Router-ID %s",
2292: IF_NAME (oi), inet_ntoa (ospfh->router_id));
2293: return 0;
2294: }
2295: return 1;
2296: case OSPF_AUTH_SIMPLE: /* RFC2328 D.5.2 */
2297: if (OSPF_AUTH_SIMPLE != (iface_auth_type = ospf_auth_type (oi)))
2298: {
2299: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2300: zlog_warn ("interface %s: auth-type mismatch, local %s, rcvd Simple",
2301: IF_NAME (oi), LOOKUP (ospf_auth_type_str, iface_auth_type));
2302: return 0;
2303: }
2304: if (memcmp (OSPF_IF_PARAM (oi, auth_simple), ospfh->u.auth_data, OSPF_AUTH_SIMPLE_SIZE))
2305: {
2306: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2307: zlog_warn ("interface %s: Simple auth failed", IF_NAME (oi));
2308: return 0;
2309: }
2310: if (! ospf_check_sum (ospfh))
2311: {
2312: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2313: zlog_warn ("interface %s: Simple auth OK, checksum error, Router-ID %s",
2314: IF_NAME (oi), inet_ntoa (ospfh->router_id));
2315: return 0;
2316: }
2317: return 1;
2318: case OSPF_AUTH_CRYPTOGRAPHIC: /* RFC2328 D.5.3 */
2319: if (OSPF_AUTH_CRYPTOGRAPHIC != (iface_auth_type = ospf_auth_type (oi)))
2320: {
2321: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2322: zlog_warn ("interface %s: auth-type mismatch, local %s, rcvd Cryptographic",
2323: IF_NAME (oi), LOOKUP (ospf_auth_type_str, iface_auth_type));
2324: return 0;
2325: }
2326: if (ospfh->checksum)
2327: {
2328: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2329: zlog_warn ("interface %s: OSPF header checksum is not 0", IF_NAME (oi));
2330: return 0;
2331: }
2332: /* only MD5 crypto method can pass ospf_packet_examin() */
2333: if
2334: (
2335: NULL == (ck = listgetdata (listtail(OSPF_IF_PARAM (oi,auth_crypt)))) ||
2336: ospfh->u.crypt.key_id != ck->key_id ||
2337: /* Condition above uses the last key ID on the list, which is
2338: different from what ospf_crypt_key_lookup() does. A bug? */
2339: ! ospf_check_md5_digest (oi, ospfh)
2340: )
2341: {
2342: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2343: zlog_warn ("interface %s: MD5 auth failed", IF_NAME (oi));
2344: return 0;
2345: }
2346: return 1;
2347: default:
2348: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2349: zlog_warn ("interface %s: invalid packet auth-type (%02x)",
2350: IF_NAME (oi), pkt_auth_type);
2351: return 0;
2352: }
2353: }
2354:
2355: static int
2356: ospf_check_sum (struct ospf_header *ospfh)
2357: {
2358: u_int32_t ret;
2359: u_int16_t sum;
2360:
2361: /* clear auth_data for checksum. */
2362: memset (ospfh->u.auth_data, 0, OSPF_AUTH_SIMPLE_SIZE);
2363:
2364: /* keep checksum and clear. */
2365: sum = ospfh->checksum;
2366: memset (&ospfh->checksum, 0, sizeof (u_int16_t));
2367:
2368: /* calculate checksum. */
2369: ret = in_cksum (ospfh, ntohs (ospfh->length));
2370:
2371: if (ret != sum)
2372: {
2373: zlog_info ("ospf_check_sum(): checksum mismatch, my %X, his %X",
2374: ret, sum);
2375: return 0;
2376: }
2377:
2378: return 1;
2379: }
2380:
2381: /* Verify, that given link/TOS records are properly sized/aligned and match
2382: Router-LSA "# links" and "# TOS" fields as specified in RFC2328 A.4.2. */
2383: static unsigned
2384: ospf_router_lsa_links_examin
2385: (
2386: struct router_lsa_link * link,
2387: u_int16_t linkbytes,
2388: const u_int16_t num_links
2389: )
2390: {
2391: unsigned counted_links = 0, thislinklen;
2392:
2393: while (linkbytes)
2394: {
2395: thislinklen = OSPF_ROUTER_LSA_LINK_SIZE + 4 * link->m[0].tos_count;
2396: if (thislinklen > linkbytes)
2397: {
2398: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2399: zlog_debug ("%s: length error in link block #%u", __func__, counted_links);
2400: return MSG_NG;
2401: }
2402: link = (struct router_lsa_link *)((caddr_t) link + thislinklen);
2403: linkbytes -= thislinklen;
2404: counted_links++;
2405: }
2406: if (counted_links != num_links)
2407: {
2408: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2409: zlog_debug ("%s: %u link blocks declared, %u present",
2410: __func__, num_links, counted_links);
2411: return MSG_NG;
2412: }
2413: return MSG_OK;
2414: }
2415:
2416: /* Verify, that the given LSA is properly sized/aligned (including type-specific
2417: minimum length constraint). */
2418: static unsigned
2419: ospf_lsa_examin (struct lsa_header * lsah, const u_int16_t lsalen, const u_char headeronly)
2420: {
2421: unsigned ret;
2422: struct router_lsa * rlsa;
2423: if
2424: (
2425: lsah->type < OSPF_MAX_LSA &&
2426: ospf_lsa_minlen[lsah->type] &&
2427: lsalen < OSPF_LSA_HEADER_SIZE + ospf_lsa_minlen[lsah->type]
2428: )
2429: {
2430: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2431: zlog_debug ("%s: undersized (%u B) %s",
2432: __func__, lsalen, LOOKUP (ospf_lsa_type_msg, lsah->type));
2433: return MSG_NG;
2434: }
2435: switch (lsah->type)
2436: {
2437: case OSPF_ROUTER_LSA:
2438: /* RFC2328 A.4.2, LSA header + 4 bytes followed by N>=1 (12+)-byte link blocks */
2439: if (headeronly)
2440: {
2441: ret = (lsalen - OSPF_LSA_HEADER_SIZE - OSPF_ROUTER_LSA_MIN_SIZE) % 4 ? MSG_NG : MSG_OK;
2442: break;
2443: }
2444: rlsa = (struct router_lsa *) lsah;
2445: ret = ospf_router_lsa_links_examin
2446: (
2447: (struct router_lsa_link *) rlsa->link,
2448: lsalen - OSPF_LSA_HEADER_SIZE - 4, /* skip: basic header, "flags", 0, "# links" */
2449: ntohs (rlsa->links) /* 16 bits */
2450: );
2451: break;
2452: case OSPF_AS_EXTERNAL_LSA:
2453: /* RFC2328 A.4.5, LSA header + 4 bytes followed by N>=1 12-bytes long blocks */
2454: case OSPF_AS_NSSA_LSA:
2455: /* RFC3101 C, idem */
2456: ret = (lsalen - OSPF_LSA_HEADER_SIZE - OSPF_AS_EXTERNAL_LSA_MIN_SIZE) % 12 ? MSG_NG : MSG_OK;
2457: break;
2458: /* Following LSA types are considered OK length-wise as soon as their minimum
2459: * length constraint is met and length of the whole LSA is a multiple of 4
2460: * (basic LSA header size is already a multiple of 4). */
2461: case OSPF_NETWORK_LSA:
2462: /* RFC2328 A.4.3, LSA header + 4 bytes followed by N>=1 router-IDs */
2463: case OSPF_SUMMARY_LSA:
2464: case OSPF_ASBR_SUMMARY_LSA:
2465: /* RFC2328 A.4.4, LSA header + 4 bytes followed by N>=1 4-bytes TOS blocks */
2466: #ifdef HAVE_OPAQUE_LSA
2467: case OSPF_OPAQUE_LINK_LSA:
2468: case OSPF_OPAQUE_AREA_LSA:
2469: case OSPF_OPAQUE_AS_LSA:
2470: /* RFC5250 A.2, "some number of octets (of application-specific
2471: * data) padded to 32-bit alignment." This is considered equivalent
2472: * to 4-byte alignment of all other LSA types, see OSPF-ALIGNMENT.txt
2473: * file for the detailed analysis of this passage. */
2474: #endif
2475: ret = lsalen % 4 ? MSG_NG : MSG_OK;
2476: break;
2477: default:
2478: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2479: zlog_debug ("%s: unsupported LSA type 0x%02x", __func__, lsah->type);
2480: return MSG_NG;
2481: }
2482: if (ret != MSG_OK && IS_DEBUG_OSPF_PACKET (0, RECV))
2483: zlog_debug ("%s: alignment error in %s",
2484: __func__, LOOKUP (ospf_lsa_type_msg, lsah->type));
2485: return ret;
2486: }
2487:
2488: /* Verify if the provided input buffer is a valid sequence of LSAs. This
2489: includes verification of LSA blocks length/alignment and dispatching
2490: of deeper-level checks. */
2491: static unsigned
2492: ospf_lsaseq_examin
2493: (
2494: struct lsa_header *lsah, /* start of buffered data */
2495: size_t length,
2496: const u_char headeronly,
2497: /* When declared_num_lsas is not 0, compare it to the real number of LSAs
2498: and treat the difference as an error. */
2499: const u_int32_t declared_num_lsas
2500: )
2501: {
2502: u_int32_t counted_lsas = 0;
2503:
2504: while (length)
2505: {
2506: u_int16_t lsalen;
2507: if (length < OSPF_LSA_HEADER_SIZE)
2508: {
2509: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2510: zlog_debug ("%s: undersized (%zu B) trailing (#%u) LSA header",
2511: __func__, length, counted_lsas);
2512: return MSG_NG;
2513: }
2514: /* save on ntohs() calls here and in the LSA validator */
2515: lsalen = ntohs (lsah->length);
2516: if (lsalen < OSPF_LSA_HEADER_SIZE)
2517: {
2518: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2519: zlog_debug ("%s: malformed LSA header #%u, declared length is %u B",
2520: __func__, counted_lsas, lsalen);
2521: return MSG_NG;
2522: }
2523: if (headeronly)
2524: {
2525: /* less checks here and in ospf_lsa_examin() */
2526: if (MSG_OK != ospf_lsa_examin (lsah, lsalen, 1))
2527: {
2528: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2529: zlog_debug ("%s: malformed header-only LSA #%u", __func__, counted_lsas);
2530: return MSG_NG;
2531: }
2532: lsah = (struct lsa_header *) ((caddr_t) lsah + OSPF_LSA_HEADER_SIZE);
2533: length -= OSPF_LSA_HEADER_SIZE;
2534: }
2535: else
2536: {
2537: /* make sure the input buffer is deep enough before further checks */
2538: if (lsalen > length)
2539: {
2540: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2541: zlog_debug ("%s: anomaly in LSA #%u: declared length is %u B, buffered length is %zu B",
2542: __func__, counted_lsas, lsalen, length);
2543: return MSG_NG;
2544: }
2545: if (MSG_OK != ospf_lsa_examin (lsah, lsalen, 0))
2546: {
2547: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2548: zlog_debug ("%s: malformed LSA #%u", __func__, counted_lsas);
2549: return MSG_NG;
2550: }
2551: lsah = (struct lsa_header *) ((caddr_t) lsah + lsalen);
2552: length -= lsalen;
2553: }
2554: counted_lsas++;
2555: }
2556:
2557: if (declared_num_lsas && counted_lsas != declared_num_lsas)
2558: {
2559: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2560: zlog_debug ("%s: #LSAs declared (%u) does not match actual (%u)",
2561: __func__, declared_num_lsas, counted_lsas);
2562: return MSG_NG;
2563: }
2564: return MSG_OK;
2565: }
2566:
2567: /* Verify a complete OSPF packet for proper sizing/alignment. */
2568: static unsigned
2569: ospf_packet_examin (struct ospf_header * oh, const unsigned bytesonwire)
2570: {
2571: u_int16_t bytesdeclared, bytesauth;
2572: unsigned ret;
2573: struct ospf_ls_update * lsupd;
2574:
2575: /* Length, 1st approximation. */
2576: if (bytesonwire < OSPF_HEADER_SIZE)
2577: {
2578: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2579: zlog_debug ("%s: undersized (%u B) packet", __func__, bytesonwire);
2580: return MSG_NG;
2581: }
2582: /* Now it is safe to access header fields. Performing length check, allow
2583: * for possible extra bytes of crypto auth/padding, which are not counted
2584: * in the OSPF header "length" field. */
2585: if (oh->version != OSPF_VERSION)
2586: {
2587: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2588: zlog_debug ("%s: invalid (%u) protocol version", __func__, oh->version);
2589: return MSG_NG;
2590: }
2591: bytesdeclared = ntohs (oh->length);
2592: if (ntohs (oh->auth_type) != OSPF_AUTH_CRYPTOGRAPHIC)
2593: bytesauth = 0;
2594: else
2595: {
2596: if (oh->u.crypt.auth_data_len != OSPF_AUTH_MD5_SIZE)
2597: {
2598: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2599: zlog_debug ("%s: unsupported crypto auth length (%u B)",
2600: __func__, oh->u.crypt.auth_data_len);
2601: return MSG_NG;
2602: }
2603: bytesauth = OSPF_AUTH_MD5_SIZE;
2604: }
2605: if (bytesdeclared + bytesauth > bytesonwire)
2606: {
2607: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2608: zlog_debug ("%s: packet length error (%u real, %u+%u declared)",
2609: __func__, bytesonwire, bytesdeclared, bytesauth);
2610: return MSG_NG;
2611: }
2612: /* Length, 2nd approximation. The type-specific constraint is checked
2613: against declared length, not amount of bytes on wire. */
2614: if
2615: (
2616: oh->type >= OSPF_MSG_HELLO &&
2617: oh->type <= OSPF_MSG_LS_ACK &&
2618: bytesdeclared < OSPF_HEADER_SIZE + ospf_packet_minlen[oh->type]
2619: )
2620: {
2621: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2622: zlog_debug ("%s: undersized (%u B) %s packet", __func__,
2623: bytesdeclared, LOOKUP (ospf_packet_type_str, oh->type));
2624: return MSG_NG;
2625: }
2626: switch (oh->type)
2627: {
2628: case OSPF_MSG_HELLO:
2629: /* RFC2328 A.3.2, packet header + OSPF_HELLO_MIN_SIZE bytes followed
2630: by N>=0 router-IDs. */
2631: ret = (bytesdeclared - OSPF_HEADER_SIZE - OSPF_HELLO_MIN_SIZE) % 4 ? MSG_NG : MSG_OK;
2632: break;
2633: case OSPF_MSG_DB_DESC:
2634: /* RFC2328 A.3.3, packet header + OSPF_DB_DESC_MIN_SIZE bytes followed
2635: by N>=0 header-only LSAs. */
2636: ret = ospf_lsaseq_examin
2637: (
2638: (struct lsa_header *) ((caddr_t) oh + OSPF_HEADER_SIZE + OSPF_DB_DESC_MIN_SIZE),
2639: bytesdeclared - OSPF_HEADER_SIZE - OSPF_DB_DESC_MIN_SIZE,
2640: 1, /* header-only LSAs */
2641: 0
2642: );
2643: break;
2644: case OSPF_MSG_LS_REQ:
2645: /* RFC2328 A.3.4, packet header followed by N>=0 12-bytes request blocks. */
2646: ret = (bytesdeclared - OSPF_HEADER_SIZE - OSPF_LS_REQ_MIN_SIZE) %
2647: OSPF_LSA_KEY_SIZE ? MSG_NG : MSG_OK;
2648: break;
2649: case OSPF_MSG_LS_UPD:
2650: /* RFC2328 A.3.5, packet header + OSPF_LS_UPD_MIN_SIZE bytes followed
2651: by N>=0 full LSAs (with N declared beforehand). */
2652: lsupd = (struct ospf_ls_update *) ((caddr_t) oh + OSPF_HEADER_SIZE);
2653: ret = ospf_lsaseq_examin
2654: (
2655: (struct lsa_header *) ((caddr_t) lsupd + OSPF_LS_UPD_MIN_SIZE),
2656: bytesdeclared - OSPF_HEADER_SIZE - OSPF_LS_UPD_MIN_SIZE,
2657: 0, /* full LSAs */
2658: ntohl (lsupd->num_lsas) /* 32 bits */
2659: );
2660: break;
2661: case OSPF_MSG_LS_ACK:
2662: /* RFC2328 A.3.6, packet header followed by N>=0 header-only LSAs. */
2663: ret = ospf_lsaseq_examin
2664: (
2665: (struct lsa_header *) ((caddr_t) oh + OSPF_HEADER_SIZE + OSPF_LS_ACK_MIN_SIZE),
2666: bytesdeclared - OSPF_HEADER_SIZE - OSPF_LS_ACK_MIN_SIZE,
2667: 1, /* header-only LSAs */
2668: 0
2669: );
2670: break;
2671: default:
2672: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2673: zlog_debug ("%s: invalid packet type 0x%02x", __func__, oh->type);
2674: return MSG_NG;
2675: }
2676: if (ret != MSG_OK && IS_DEBUG_OSPF_PACKET (0, RECV))
2677: zlog_debug ("%s: malformed %s packet", __func__, LOOKUP (ospf_packet_type_str, oh->type));
2678: return ret;
2679: }
2680:
2681: /* OSPF Header verification. */
2682: static int
2683: ospf_verify_header (struct stream *ibuf, struct ospf_interface *oi,
2684: struct ip *iph, struct ospf_header *ospfh)
2685: {
2686: /* Check Area ID. */
2687: if (!ospf_check_area_id (oi, ospfh))
2688: {
2689: zlog_warn ("interface %s: ospf_read invalid Area ID %s.",
2690: IF_NAME (oi), inet_ntoa (ospfh->area_id));
2691: return -1;
2692: }
2693:
2694: /* Check network mask, Silently discarded. */
2695: if (! ospf_check_network_mask (oi, iph->ip_src))
2696: {
2697: zlog_warn ("interface %s: ospf_read network address is not same [%s]",
2698: IF_NAME (oi), inet_ntoa (iph->ip_src));
2699: return -1;
2700: }
2701:
2702: /* Check authentication. The function handles logging actions, where required. */
2703: if (! ospf_check_auth (oi, ospfh))
2704: return -1;
2705:
2706: return 0;
2707: }
2708:
2709: /* Starting point of packet process function. */
2710: int
2711: ospf_read (struct thread *thread)
2712: {
2713: int ret;
2714: struct stream *ibuf;
2715: struct ospf *ospf;
2716: struct ospf_interface *oi;
2717: struct ip *iph;
2718: struct ospf_header *ospfh;
2719: u_int16_t length;
2720: struct interface *ifp;
2721:
2722: /* first of all get interface pointer. */
2723: ospf = THREAD_ARG (thread);
2724:
2725: /* prepare for next packet. */
2726: ospf->t_read = thread_add_read (master, ospf_read, ospf, ospf->fd);
2727:
2728: stream_reset(ospf->ibuf);
2729: if (!(ibuf = ospf_recv_packet (ospf->fd, &ifp, ospf->ibuf)))
2730: return -1;
2731: /* This raw packet is known to be at least as big as its IP header. */
2732:
2733: /* Note that there should not be alignment problems with this assignment
2734: because this is at the beginning of the stream data buffer. */
2735: iph = (struct ip *) STREAM_DATA (ibuf);
2736: /* Note that sockopt_iphdrincl_swab_systoh was called in ospf_recv_packet. */
2737:
2738: if (ifp == NULL)
2739: /* Handle cases where the platform does not support retrieving the ifindex,
2740: and also platforms (such as Solaris 8) that claim to support ifindex
2741: retrieval but do not. */
2742: ifp = if_lookup_address (iph->ip_src);
2743:
2744: if (ifp == NULL)
2745: return 0;
2746:
2747: /* IP Header dump. */
2748: if (IS_DEBUG_OSPF_PACKET(0, RECV))
2749: ospf_ip_header_dump (iph);
2750:
2751: /* Self-originated packet should be discarded silently. */
2752: if (ospf_if_lookup_by_local_addr (ospf, NULL, iph->ip_src))
2753: {
2754: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2755: {
2756: zlog_debug ("ospf_read[%s]: Dropping self-originated packet",
2757: inet_ntoa (iph->ip_src));
2758: }
2759: return 0;
2760: }
2761:
2762: /* Advance from IP header to OSPF header (iph->ip_hl has been verified
2763: by ospf_recv_packet() to be correct). */
2764: stream_forward_getp (ibuf, iph->ip_hl * 4);
2765:
2766: ospfh = (struct ospf_header *) STREAM_PNT (ibuf);
2767: if (MSG_OK != ospf_packet_examin (ospfh, stream_get_endp (ibuf) - stream_get_getp (ibuf)))
2768: return -1;
2769: /* Now it is safe to access all fields of OSPF packet header. */
2770:
2771: /* associate packet with ospf interface */
2772: oi = ospf_if_lookup_recv_if (ospf, iph->ip_src, ifp);
2773:
2774: /* ospf_verify_header() relies on a valid "oi" and thus can be called only
2775: after the passive/backbone/other checks below are passed. These checks
2776: in turn access the fields of unverified "ospfh" structure for their own
2777: purposes and must remain very accurate in doing this. */
2778:
2779: /* If incoming interface is passive one, ignore it. */
2780: if (oi && OSPF_IF_PASSIVE_STATUS (oi) == OSPF_IF_PASSIVE)
2781: {
2782: char buf[3][INET_ADDRSTRLEN];
2783:
2784: if (IS_DEBUG_OSPF_EVENT)
2785: zlog_debug ("ignoring packet from router %s sent to %s, "
2786: "received on a passive interface, %s",
2787: inet_ntop(AF_INET, &ospfh->router_id, buf[0], sizeof(buf[0])),
2788: inet_ntop(AF_INET, &iph->ip_dst, buf[1], sizeof(buf[1])),
2789: inet_ntop(AF_INET, &oi->address->u.prefix4,
2790: buf[2], sizeof(buf[2])));
2791:
2792: if (iph->ip_dst.s_addr == htonl(OSPF_ALLSPFROUTERS))
2793: {
2794: /* Try to fix multicast membership.
2795: * Some OS:es may have problems in this area,
2796: * make sure it is removed.
2797: */
2798: OI_MEMBER_JOINED(oi, MEMBER_ALLROUTERS);
2799: ospf_if_set_multicast(oi);
2800: }
2801: return 0;
2802: }
2803:
2804:
2805: /* if no local ospf_interface,
2806: * or header area is backbone but ospf_interface is not
2807: * check for VLINK interface
2808: */
2809: if ( (oi == NULL) ||
2810: (OSPF_IS_AREA_ID_BACKBONE(ospfh->area_id)
2811: && !OSPF_IS_AREA_ID_BACKBONE(oi->area->area_id))
2812: )
2813: {
2814: if ((oi = ospf_associate_packet_vl (ospf, ifp, iph, ospfh)) == NULL)
2815: {
2816: if (IS_DEBUG_OSPF_EVENT)
2817: zlog_debug ("Packet from [%s] received on link %s"
2818: " but no ospf_interface",
2819: inet_ntoa (iph->ip_src), ifp->name);
2820: return 0;
2821: }
2822: }
2823:
2824: /* else it must be a local ospf interface, check it was received on
2825: * correct link
2826: */
2827: else if (oi->ifp != ifp)
2828: {
2829: if (IS_DEBUG_OSPF_EVENT)
2830: zlog_warn ("Packet from [%s] received on wrong link %s",
2831: inet_ntoa (iph->ip_src), ifp->name);
2832: return 0;
2833: }
2834: else if (oi->state == ISM_Down)
2835: {
2836: char buf[2][INET_ADDRSTRLEN];
2837: zlog_warn ("Ignoring packet from %s to %s received on interface that is "
2838: "down [%s]; interface flags are %s",
2839: inet_ntop(AF_INET, &iph->ip_src, buf[0], sizeof(buf[0])),
2840: inet_ntop(AF_INET, &iph->ip_dst, buf[1], sizeof(buf[1])),
2841: ifp->name, if_flag_dump(ifp->flags));
2842: /* Fix multicast memberships? */
2843: if (iph->ip_dst.s_addr == htonl(OSPF_ALLSPFROUTERS))
2844: OI_MEMBER_JOINED(oi, MEMBER_ALLROUTERS);
2845: else if (iph->ip_dst.s_addr == htonl(OSPF_ALLDROUTERS))
2846: OI_MEMBER_JOINED(oi, MEMBER_DROUTERS);
2847: if (oi->multicast_memberships)
2848: ospf_if_set_multicast(oi);
2849: return 0;
2850: }
2851:
2852: /*
2853: * If the received packet is destined for AllDRouters, the packet
2854: * should be accepted only if the received ospf interface state is
2855: * either DR or Backup -- endo.
2856: */
2857: if (iph->ip_dst.s_addr == htonl (OSPF_ALLDROUTERS)
2858: && (oi->state != ISM_DR && oi->state != ISM_Backup))
2859: {
2860: zlog_warn ("Dropping packet for AllDRouters from [%s] via [%s] (ISM: %s)",
2861: inet_ntoa (iph->ip_src), IF_NAME (oi),
2862: LOOKUP (ospf_ism_state_msg, oi->state));
2863: /* Try to fix multicast membership. */
2864: SET_FLAG(oi->multicast_memberships, MEMBER_DROUTERS);
2865: ospf_if_set_multicast(oi);
2866: return 0;
2867: }
2868:
2869: /* Verify more OSPF header fields. */
2870: ret = ospf_verify_header (ibuf, oi, iph, ospfh);
2871: if (ret < 0)
2872: {
2873: if (IS_DEBUG_OSPF_PACKET (0, RECV))
2874: zlog_debug ("ospf_read[%s]: Header check failed, "
2875: "dropping.",
2876: inet_ntoa (iph->ip_src));
2877: return ret;
2878: }
2879:
2880: /* Show debug receiving packet. */
2881: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, RECV))
2882: {
2883: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, DETAIL))
2884: {
2885: zlog_debug ("-----------------------------------------------------");
2886: ospf_packet_dump (ibuf);
2887: }
2888:
2889: zlog_debug ("%s received from [%s] via [%s]",
2890: LOOKUP (ospf_packet_type_str, ospfh->type),
2891: inet_ntoa (ospfh->router_id), IF_NAME (oi));
2892: zlog_debug (" src [%s],", inet_ntoa (iph->ip_src));
2893: zlog_debug (" dst [%s]", inet_ntoa (iph->ip_dst));
2894:
2895: if (IS_DEBUG_OSPF_PACKET (ospfh->type - 1, DETAIL))
2896: zlog_debug ("-----------------------------------------------------");
2897: }
2898:
2899: stream_forward_getp (ibuf, OSPF_HEADER_SIZE);
2900:
2901: /* Adjust size to message length. */
2902: length = ntohs (ospfh->length) - OSPF_HEADER_SIZE;
2903:
2904: /* Read rest of the packet and call each sort of packet routine. */
2905: switch (ospfh->type)
2906: {
2907: case OSPF_MSG_HELLO:
2908: ospf_hello (iph, ospfh, ibuf, oi, length);
2909: break;
2910: case OSPF_MSG_DB_DESC:
2911: ospf_db_desc (iph, ospfh, ibuf, oi, length);
2912: break;
2913: case OSPF_MSG_LS_REQ:
2914: ospf_ls_req (iph, ospfh, ibuf, oi, length);
2915: break;
2916: case OSPF_MSG_LS_UPD:
2917: ospf_ls_upd (iph, ospfh, ibuf, oi, length);
2918: break;
2919: case OSPF_MSG_LS_ACK:
2920: ospf_ls_ack (iph, ospfh, ibuf, oi, length);
2921: break;
2922: default:
2923: zlog (NULL, LOG_WARNING,
2924: "interface %s: OSPF packet header type %d is illegal",
2925: IF_NAME (oi), ospfh->type);
2926: break;
2927: }
2928:
2929: return 0;
2930: }
2931:
2932: /* Make OSPF header. */
2933: static void
2934: ospf_make_header (int type, struct ospf_interface *oi, struct stream *s)
2935: {
2936: struct ospf_header *ospfh;
2937:
2938: ospfh = (struct ospf_header *) STREAM_DATA (s);
2939:
2940: ospfh->version = (u_char) OSPF_VERSION;
2941: ospfh->type = (u_char) type;
2942:
2943: ospfh->router_id = oi->ospf->router_id;
2944:
2945: ospfh->checksum = 0;
2946: ospfh->area_id = oi->area->area_id;
2947: ospfh->auth_type = htons (ospf_auth_type (oi));
2948:
2949: memset (ospfh->u.auth_data, 0, OSPF_AUTH_SIMPLE_SIZE);
2950:
2951: stream_forward_endp (s, OSPF_HEADER_SIZE);
2952: }
2953:
2954: /* Make Authentication Data. */
2955: static int
2956: ospf_make_auth (struct ospf_interface *oi, struct ospf_header *ospfh)
2957: {
2958: struct crypt_key *ck;
2959:
2960: switch (ospf_auth_type (oi))
2961: {
2962: case OSPF_AUTH_NULL:
2963: /* memset (ospfh->u.auth_data, 0, sizeof (ospfh->u.auth_data)); */
2964: break;
2965: case OSPF_AUTH_SIMPLE:
2966: memcpy (ospfh->u.auth_data, OSPF_IF_PARAM (oi, auth_simple),
2967: OSPF_AUTH_SIMPLE_SIZE);
2968: break;
2969: case OSPF_AUTH_CRYPTOGRAPHIC:
2970: /* If key is not set, then set 0. */
2971: if (list_isempty (OSPF_IF_PARAM (oi, auth_crypt)))
2972: {
2973: ospfh->u.crypt.zero = 0;
2974: ospfh->u.crypt.key_id = 0;
2975: ospfh->u.crypt.auth_data_len = OSPF_AUTH_MD5_SIZE;
2976: }
2977: else
2978: {
2979: ck = listgetdata (listtail(OSPF_IF_PARAM (oi, auth_crypt)));
2980: ospfh->u.crypt.zero = 0;
2981: ospfh->u.crypt.key_id = ck->key_id;
2982: ospfh->u.crypt.auth_data_len = OSPF_AUTH_MD5_SIZE;
2983: }
2984: /* note: the seq is done in ospf_make_md5_digest() */
2985: break;
2986: default:
2987: /* memset (ospfh->u.auth_data, 0, sizeof (ospfh->u.auth_data)); */
2988: break;
2989: }
2990:
2991: return 0;
2992: }
2993:
2994: /* Fill rest of OSPF header. */
2995: static void
2996: ospf_fill_header (struct ospf_interface *oi,
2997: struct stream *s, u_int16_t length)
2998: {
2999: struct ospf_header *ospfh;
3000:
3001: ospfh = (struct ospf_header *) STREAM_DATA (s);
3002:
3003: /* Fill length. */
3004: ospfh->length = htons (length);
3005:
3006: /* Calculate checksum. */
3007: if (ntohs (ospfh->auth_type) != OSPF_AUTH_CRYPTOGRAPHIC)
3008: ospfh->checksum = in_cksum (ospfh, length);
3009: else
3010: ospfh->checksum = 0;
3011:
3012: /* Add Authentication Data. */
3013: ospf_make_auth (oi, ospfh);
3014: }
3015:
3016: static int
3017: ospf_make_hello (struct ospf_interface *oi, struct stream *s)
3018: {
3019: struct ospf_neighbor *nbr;
3020: struct route_node *rn;
3021: u_int16_t length = OSPF_HELLO_MIN_SIZE;
3022: struct in_addr mask;
3023: unsigned long p;
3024: int flag = 0;
3025:
3026: /* Set netmask of interface. */
3027: if (oi->type != OSPF_IFTYPE_POINTOPOINT &&
3028: oi->type != OSPF_IFTYPE_VIRTUALLINK)
3029: masklen2ip (oi->address->prefixlen, &mask);
3030: else
3031: memset ((char *) &mask, 0, sizeof (struct in_addr));
3032: stream_put_ipv4 (s, mask.s_addr);
3033:
3034: /* Set Hello Interval. */
3035: if (OSPF_IF_PARAM (oi, fast_hello) == 0)
3036: stream_putw (s, OSPF_IF_PARAM (oi, v_hello));
3037: else
3038: stream_putw (s, 0); /* hello-interval of 0 for fast-hellos */
3039:
3040: if (IS_DEBUG_OSPF_EVENT)
3041: zlog_debug ("make_hello: options: %x, int: %s",
3042: OPTIONS(oi), IF_NAME (oi));
3043:
3044: /* Set Options. */
3045: stream_putc (s, OPTIONS (oi));
3046:
3047: /* Set Router Priority. */
3048: stream_putc (s, PRIORITY (oi));
3049:
3050: /* Set Router Dead Interval. */
3051: stream_putl (s, OSPF_IF_PARAM (oi, v_wait));
3052:
3053: /* Set Designated Router. */
3054: stream_put_ipv4 (s, DR (oi).s_addr);
3055:
3056: p = stream_get_endp (s);
3057:
3058: /* Set Backup Designated Router. */
3059: stream_put_ipv4 (s, BDR (oi).s_addr);
3060:
3061: /* Add neighbor seen. */
3062: for (rn = route_top (oi->nbrs); rn; rn = route_next (rn))
3063: if ((nbr = rn->info))
3064: if (nbr->router_id.s_addr != 0) /* Ignore 0.0.0.0 node. */
3065: if (nbr->state != NSM_Attempt) /* Ignore Down neighbor. */
3066: if (nbr->state != NSM_Down) /* This is myself for DR election. */
3067: if (!IPV4_ADDR_SAME (&nbr->router_id, &oi->ospf->router_id))
3068: {
3069: /* Check neighbor is sane? */
3070: if (nbr->d_router.s_addr != 0
3071: && IPV4_ADDR_SAME (&nbr->d_router, &oi->address->u.prefix4)
3072: && IPV4_ADDR_SAME (&nbr->bd_router, &oi->address->u.prefix4))
3073: flag = 1;
3074:
3075: stream_put_ipv4 (s, nbr->router_id.s_addr);
3076: length += 4;
3077: }
3078:
3079: /* Let neighbor generate BackupSeen. */
3080: if (flag == 1)
3081: stream_putl_at (s, p, 0); /* ipv4 address, normally */
3082:
3083: return length;
3084: }
3085:
3086: static int
3087: ospf_make_db_desc (struct ospf_interface *oi, struct ospf_neighbor *nbr,
3088: struct stream *s)
3089: {
3090: struct ospf_lsa *lsa;
3091: u_int16_t length = OSPF_DB_DESC_MIN_SIZE;
3092: u_char options;
3093: unsigned long pp;
3094: int i;
3095: struct ospf_lsdb *lsdb;
3096:
3097: /* Set Interface MTU. */
3098: if (oi->type == OSPF_IFTYPE_VIRTUALLINK)
3099: stream_putw (s, 0);
3100: else
3101: stream_putw (s, oi->ifp->mtu);
3102:
3103: /* Set Options. */
3104: options = OPTIONS (oi);
3105: #ifdef HAVE_OPAQUE_LSA
3106: if (CHECK_FLAG (oi->ospf->config, OSPF_OPAQUE_CAPABLE))
3107: {
3108: if (IS_SET_DD_I (nbr->dd_flags)
3109: || CHECK_FLAG (nbr->options, OSPF_OPTION_O))
3110: /*
3111: * Set O-bit in the outgoing DD packet for capablity negotiation,
3112: * if one of following case is applicable.
3113: *
3114: * 1) WaitTimer expiration event triggered the neighbor state to
3115: * change to Exstart, but no (valid) DD packet has received
3116: * from the neighbor yet.
3117: *
3118: * 2) At least one DD packet with O-bit on has received from the
3119: * neighbor.
3120: */
3121: SET_FLAG (options, OSPF_OPTION_O);
3122: }
3123: #endif /* HAVE_OPAQUE_LSA */
3124: stream_putc (s, options);
3125:
3126: /* DD flags */
3127: pp = stream_get_endp (s);
3128: stream_putc (s, nbr->dd_flags);
3129:
3130: /* Set DD Sequence Number. */
3131: stream_putl (s, nbr->dd_seqnum);
3132:
3133: /* shortcut unneeded walk of (empty) summary LSDBs */
3134: if (ospf_db_summary_isempty (nbr))
3135: goto empty;
3136:
3137: /* Describe LSA Header from Database Summary List. */
3138: lsdb = &nbr->db_sum;
3139:
3140: for (i = OSPF_MIN_LSA; i < OSPF_MAX_LSA; i++)
3141: {
3142: struct route_table *table = lsdb->type[i].db;
3143: struct route_node *rn;
3144:
3145: for (rn = route_top (table); rn; rn = route_next (rn))
3146: if ((lsa = rn->info) != NULL)
3147: {
3148: #ifdef HAVE_OPAQUE_LSA
3149: if (IS_OPAQUE_LSA (lsa->data->type)
3150: && (! CHECK_FLAG (options, OSPF_OPTION_O)))
3151: {
3152: /* Suppress advertising opaque-informations. */
3153: /* Remove LSA from DB summary list. */
3154: ospf_lsdb_delete (lsdb, lsa);
3155: continue;
3156: }
3157: #endif /* HAVE_OPAQUE_LSA */
3158:
3159: if (!CHECK_FLAG (lsa->flags, OSPF_LSA_DISCARD))
3160: {
3161: struct lsa_header *lsah;
3162: u_int16_t ls_age;
3163:
3164: /* DD packet overflows interface MTU. */
3165: if (length + OSPF_LSA_HEADER_SIZE > ospf_packet_max (oi))
3166: break;
3167:
3168: /* Keep pointer to LS age. */
3169: lsah = (struct lsa_header *) (STREAM_DATA (s) +
3170: stream_get_endp (s));
3171:
3172: /* Proceed stream pointer. */
3173: stream_put (s, lsa->data, OSPF_LSA_HEADER_SIZE);
3174: length += OSPF_LSA_HEADER_SIZE;
3175:
3176: /* Set LS age. */
3177: ls_age = LS_AGE (lsa);
3178: lsah->ls_age = htons (ls_age);
3179:
3180: }
3181:
3182: /* Remove LSA from DB summary list. */
3183: ospf_lsdb_delete (lsdb, lsa);
3184: }
3185: }
3186:
3187: /* Update 'More' bit */
3188: if (ospf_db_summary_isempty (nbr))
3189: {
3190: empty:
3191: if (nbr->state >= NSM_Exchange)
3192: {
3193: UNSET_FLAG (nbr->dd_flags, OSPF_DD_FLAG_M);
3194: /* Rewrite DD flags */
3195: stream_putc_at (s, pp, nbr->dd_flags);
3196: }
3197: else
3198: {
3199: assert (IS_SET_DD_M(nbr->dd_flags));
3200: }
3201: }
3202: return length;
3203: }
3204:
3205: static int
3206: ospf_make_ls_req_func (struct stream *s, u_int16_t *length,
3207: unsigned long delta, struct ospf_neighbor *nbr,
3208: struct ospf_lsa *lsa)
3209: {
3210: struct ospf_interface *oi;
3211:
3212: oi = nbr->oi;
3213:
3214: /* LS Request packet overflows interface MTU. */
3215: if (*length + delta > ospf_packet_max(oi))
3216: return 0;
3217:
3218: stream_putl (s, lsa->data->type);
3219: stream_put_ipv4 (s, lsa->data->id.s_addr);
3220: stream_put_ipv4 (s, lsa->data->adv_router.s_addr);
3221:
3222: ospf_lsa_unlock (&nbr->ls_req_last);
3223: nbr->ls_req_last = ospf_lsa_lock (lsa);
3224:
3225: *length += 12;
3226: return 1;
3227: }
3228:
3229: static int
3230: ospf_make_ls_req (struct ospf_neighbor *nbr, struct stream *s)
3231: {
3232: struct ospf_lsa *lsa;
3233: u_int16_t length = OSPF_LS_REQ_MIN_SIZE;
3234: unsigned long delta = stream_get_endp(s)+12;
3235: struct route_table *table;
3236: struct route_node *rn;
3237: int i;
3238: struct ospf_lsdb *lsdb;
3239:
3240: lsdb = &nbr->ls_req;
3241:
3242: for (i = OSPF_MIN_LSA; i < OSPF_MAX_LSA; i++)
3243: {
3244: table = lsdb->type[i].db;
3245: for (rn = route_top (table); rn; rn = route_next (rn))
3246: if ((lsa = (rn->info)) != NULL)
3247: if (ospf_make_ls_req_func (s, &length, delta, nbr, lsa) == 0)
3248: {
3249: route_unlock_node (rn);
3250: break;
3251: }
3252: }
3253: return length;
3254: }
3255:
3256: static int
3257: ls_age_increment (struct ospf_lsa *lsa, int delay)
3258: {
3259: int age;
3260:
3261: age = IS_LSA_MAXAGE (lsa) ? OSPF_LSA_MAXAGE : LS_AGE (lsa) + delay;
3262:
3263: return (age > OSPF_LSA_MAXAGE ? OSPF_LSA_MAXAGE : age);
3264: }
3265:
3266: static int
3267: ospf_make_ls_upd (struct ospf_interface *oi, struct list *update, struct stream *s)
3268: {
3269: struct ospf_lsa *lsa;
3270: struct listnode *node;
3271: u_int16_t length = 0;
3272: unsigned int size_noauth;
3273: unsigned long delta = stream_get_endp (s);
3274: unsigned long pp;
3275: int count = 0;
3276:
3277: if (IS_DEBUG_OSPF_EVENT)
3278: zlog_debug ("ospf_make_ls_upd: Start");
3279:
3280: pp = stream_get_endp (s);
3281: stream_forward_endp (s, OSPF_LS_UPD_MIN_SIZE);
3282: length += OSPF_LS_UPD_MIN_SIZE;
3283:
3284: /* Calculate amount of packet usable for data. */
3285: size_noauth = stream_get_size(s) - ospf_packet_authspace(oi);
3286:
3287: while ((node = listhead (update)) != NULL)
3288: {
3289: struct lsa_header *lsah;
3290: u_int16_t ls_age;
3291:
3292: if (IS_DEBUG_OSPF_EVENT)
3293: zlog_debug ("ospf_make_ls_upd: List Iteration");
3294:
3295: lsa = listgetdata (node);
3296:
3297: assert (lsa->data);
3298:
3299: /* Will it fit? */
3300: if (length + delta + ntohs (lsa->data->length) > size_noauth)
3301: break;
3302:
3303: /* Keep pointer to LS age. */
3304: lsah = (struct lsa_header *) (STREAM_DATA (s) + stream_get_endp (s));
3305:
3306: /* Put LSA to Link State Request. */
3307: stream_put (s, lsa->data, ntohs (lsa->data->length));
3308:
3309: /* Set LS age. */
3310: /* each hop must increment an lsa_age by transmit_delay
3311: of OSPF interface */
3312: ls_age = ls_age_increment (lsa, OSPF_IF_PARAM (oi, transmit_delay));
3313: lsah->ls_age = htons (ls_age);
3314:
3315: length += ntohs (lsa->data->length);
3316: count++;
3317:
3318: list_delete_node (update, node);
3319: ospf_lsa_unlock (&lsa); /* oi->ls_upd_queue */
3320: }
3321:
3322: /* Now set #LSAs. */
3323: stream_putl_at (s, pp, count);
3324:
3325: if (IS_DEBUG_OSPF_EVENT)
3326: zlog_debug ("ospf_make_ls_upd: Stop");
3327: return length;
3328: }
3329:
3330: static int
3331: ospf_make_ls_ack (struct ospf_interface *oi, struct list *ack, struct stream *s)
3332: {
3333: struct listnode *node, *nnode;
3334: u_int16_t length = OSPF_LS_ACK_MIN_SIZE;
3335: unsigned long delta = stream_get_endp(s) + 24;
3336: struct ospf_lsa *lsa;
3337:
3338: for (ALL_LIST_ELEMENTS (ack, node, nnode, lsa))
3339: {
3340: assert (lsa);
3341:
3342: if (length + delta > ospf_packet_max (oi))
3343: break;
3344:
3345: stream_put (s, lsa->data, OSPF_LSA_HEADER_SIZE);
3346: length += OSPF_LSA_HEADER_SIZE;
3347:
3348: listnode_delete (ack, lsa);
3349: ospf_lsa_unlock (&lsa); /* oi->ls_ack_direct.ls_ack */
3350: }
3351:
3352: return length;
3353: }
3354:
3355: static void
3356: ospf_hello_send_sub (struct ospf_interface *oi, in_addr_t addr)
3357: {
3358: struct ospf_packet *op;
3359: u_int16_t length = OSPF_HEADER_SIZE;
3360:
3361: op = ospf_packet_new (oi->ifp->mtu);
3362:
3363: /* Prepare OSPF common header. */
3364: ospf_make_header (OSPF_MSG_HELLO, oi, op->s);
3365:
3366: /* Prepare OSPF Hello body. */
3367: length += ospf_make_hello (oi, op->s);
3368:
3369: /* Fill OSPF header. */
3370: ospf_fill_header (oi, op->s, length);
3371:
3372: /* Set packet length. */
3373: op->length = length;
3374:
3375: op->dst.s_addr = addr;
3376:
3377: /* Add packet to the top of the interface output queue, so that they
3378: * can't get delayed by things like long queues of LS Update packets
3379: */
3380: ospf_packet_add_top (oi, op);
3381:
3382: /* Hook thread to write packet. */
3383: OSPF_ISM_WRITE_ON (oi->ospf);
3384: }
3385:
3386: static void
3387: ospf_poll_send (struct ospf_nbr_nbma *nbr_nbma)
3388: {
3389: struct ospf_interface *oi;
3390:
3391: oi = nbr_nbma->oi;
3392: assert(oi);
3393:
3394: /* If this is passive interface, do not send OSPF Hello. */
3395: if (OSPF_IF_PASSIVE_STATUS (oi) == OSPF_IF_PASSIVE)
3396: return;
3397:
3398: if (oi->type != OSPF_IFTYPE_NBMA)
3399: return;
3400:
3401: if (nbr_nbma->nbr != NULL && nbr_nbma->nbr->state != NSM_Down)
3402: return;
3403:
3404: if (PRIORITY(oi) == 0)
3405: return;
3406:
3407: if (nbr_nbma->priority == 0
3408: && oi->state != ISM_DR && oi->state != ISM_Backup)
3409: return;
3410:
3411: ospf_hello_send_sub (oi, nbr_nbma->addr.s_addr);
3412: }
3413:
3414: int
3415: ospf_poll_timer (struct thread *thread)
3416: {
3417: struct ospf_nbr_nbma *nbr_nbma;
3418:
3419: nbr_nbma = THREAD_ARG (thread);
3420: nbr_nbma->t_poll = NULL;
3421:
3422: if (IS_DEBUG_OSPF (nsm, NSM_TIMERS))
3423: zlog (NULL, LOG_DEBUG, "NSM[%s:%s]: Timer (Poll timer expire)",
3424: IF_NAME (nbr_nbma->oi), inet_ntoa (nbr_nbma->addr));
3425:
3426: ospf_poll_send (nbr_nbma);
3427:
3428: if (nbr_nbma->v_poll > 0)
3429: OSPF_POLL_TIMER_ON (nbr_nbma->t_poll, ospf_poll_timer,
3430: nbr_nbma->v_poll);
3431:
3432: return 0;
3433: }
3434:
3435:
3436: int
3437: ospf_hello_reply_timer (struct thread *thread)
3438: {
3439: struct ospf_neighbor *nbr;
3440:
3441: nbr = THREAD_ARG (thread);
3442: nbr->t_hello_reply = NULL;
3443:
3444: assert (nbr->oi);
3445:
3446: if (IS_DEBUG_OSPF (nsm, NSM_TIMERS))
3447: zlog (NULL, LOG_DEBUG, "NSM[%s:%s]: Timer (hello-reply timer expire)",
3448: IF_NAME (nbr->oi), inet_ntoa (nbr->router_id));
3449:
3450: ospf_hello_send_sub (nbr->oi, nbr->address.u.prefix4.s_addr);
3451:
3452: return 0;
3453: }
3454:
3455: /* Send OSPF Hello. */
3456: void
3457: ospf_hello_send (struct ospf_interface *oi)
3458: {
3459: /* If this is passive interface, do not send OSPF Hello. */
3460: if (OSPF_IF_PASSIVE_STATUS (oi) == OSPF_IF_PASSIVE)
3461: return;
3462:
3463: if (oi->type == OSPF_IFTYPE_NBMA)
3464: {
3465: struct ospf_neighbor *nbr;
3466: struct route_node *rn;
3467:
3468: for (rn = route_top (oi->nbrs); rn; rn = route_next (rn))
3469: if ((nbr = rn->info))
3470: if (nbr != oi->nbr_self)
3471: if (nbr->state != NSM_Down)
3472: {
3473: /* RFC 2328 Section 9.5.1
3474: If the router is not eligible to become Designated Router,
3475: it must periodically send Hello Packets to both the
3476: Designated Router and the Backup Designated Router (if they
3477: exist). */
3478: if (PRIORITY(oi) == 0 &&
3479: IPV4_ADDR_CMP(&DR(oi), &nbr->address.u.prefix4) &&
3480: IPV4_ADDR_CMP(&BDR(oi), &nbr->address.u.prefix4))
3481: continue;
3482:
3483: /* If the router is eligible to become Designated Router, it
3484: must periodically send Hello Packets to all neighbors that
3485: are also eligible. In addition, if the router is itself the
3486: Designated Router or Backup Designated Router, it must also
3487: send periodic Hello Packets to all other neighbors. */
3488:
3489: if (nbr->priority == 0 && oi->state == ISM_DROther)
3490: continue;
3491: /* if oi->state == Waiting, send hello to all neighbors */
3492: ospf_hello_send_sub (oi, nbr->address.u.prefix4.s_addr);
3493: }
3494: }
3495: else
3496: {
3497: /* Decide destination address. */
3498: if (oi->type == OSPF_IFTYPE_VIRTUALLINK)
3499: ospf_hello_send_sub (oi, oi->vl_data->peer_addr.s_addr);
3500: else
3501: ospf_hello_send_sub (oi, htonl (OSPF_ALLSPFROUTERS));
3502: }
3503: }
3504:
3505: /* Send OSPF Database Description. */
3506: void
3507: ospf_db_desc_send (struct ospf_neighbor *nbr)
3508: {
3509: struct ospf_interface *oi;
3510: struct ospf_packet *op;
3511: u_int16_t length = OSPF_HEADER_SIZE;
3512:
3513: oi = nbr->oi;
3514: op = ospf_packet_new (oi->ifp->mtu);
3515:
3516: /* Prepare OSPF common header. */
3517: ospf_make_header (OSPF_MSG_DB_DESC, oi, op->s);
3518:
3519: /* Prepare OSPF Database Description body. */
3520: length += ospf_make_db_desc (oi, nbr, op->s);
3521:
3522: /* Fill OSPF header. */
3523: ospf_fill_header (oi, op->s, length);
3524:
3525: /* Set packet length. */
3526: op->length = length;
3527:
3528: /* Decide destination address. */
3529: if (oi->type == OSPF_IFTYPE_POINTOPOINT)
3530: op->dst.s_addr = htonl (OSPF_ALLSPFROUTERS);
3531: else
3532: op->dst = nbr->address.u.prefix4;
3533:
3534: /* Add packet to the interface output queue. */
3535: ospf_packet_add (oi, op);
3536:
3537: /* Hook thread to write packet. */
3538: OSPF_ISM_WRITE_ON (oi->ospf);
3539:
3540: /* Remove old DD packet, then copy new one and keep in neighbor structure. */
3541: if (nbr->last_send)
3542: ospf_packet_free (nbr->last_send);
3543: nbr->last_send = ospf_packet_dup (op);
3544: quagga_gettime (QUAGGA_CLK_MONOTONIC, &nbr->last_send_ts);
3545: }
3546:
3547: /* Re-send Database Description. */
3548: void
3549: ospf_db_desc_resend (struct ospf_neighbor *nbr)
3550: {
3551: struct ospf_interface *oi;
3552:
3553: oi = nbr->oi;
3554:
3555: /* Add packet to the interface output queue. */
3556: ospf_packet_add (oi, ospf_packet_dup (nbr->last_send));
3557:
3558: /* Hook thread to write packet. */
3559: OSPF_ISM_WRITE_ON (oi->ospf);
3560: }
3561:
3562: /* Send Link State Request. */
3563: void
3564: ospf_ls_req_send (struct ospf_neighbor *nbr)
3565: {
3566: struct ospf_interface *oi;
3567: struct ospf_packet *op;
3568: u_int16_t length = OSPF_HEADER_SIZE;
3569:
3570: oi = nbr->oi;
3571: op = ospf_packet_new (oi->ifp->mtu);
3572:
3573: /* Prepare OSPF common header. */
3574: ospf_make_header (OSPF_MSG_LS_REQ, oi, op->s);
3575:
3576: /* Prepare OSPF Link State Request body. */
3577: length += ospf_make_ls_req (nbr, op->s);
3578: if (length == OSPF_HEADER_SIZE)
3579: {
3580: ospf_packet_free (op);
3581: return;
3582: }
3583:
3584: /* Fill OSPF header. */
3585: ospf_fill_header (oi, op->s, length);
3586:
3587: /* Set packet length. */
3588: op->length = length;
3589:
3590: /* Decide destination address. */
3591: if (oi->type == OSPF_IFTYPE_POINTOPOINT)
3592: op->dst.s_addr = htonl (OSPF_ALLSPFROUTERS);
3593: else
3594: op->dst = nbr->address.u.prefix4;
3595:
3596: /* Add packet to the interface output queue. */
3597: ospf_packet_add (oi, op);
3598:
3599: /* Hook thread to write packet. */
3600: OSPF_ISM_WRITE_ON (oi->ospf);
3601:
3602: /* Add Link State Request Retransmission Timer. */
3603: OSPF_NSM_TIMER_ON (nbr->t_ls_req, ospf_ls_req_timer, nbr->v_ls_req);
3604: }
3605:
3606: /* Send Link State Update with an LSA. */
3607: void
3608: ospf_ls_upd_send_lsa (struct ospf_neighbor *nbr, struct ospf_lsa *lsa,
3609: int flag)
3610: {
3611: struct list *update;
3612:
3613: update = list_new ();
3614:
3615: listnode_add (update, lsa);
3616: ospf_ls_upd_send (nbr, update, flag);
3617:
3618: list_delete (update);
3619: }
3620:
3621: /* Determine size for packet. Must be at least big enough to accomodate next
3622: * LSA on list, which may be bigger than MTU size.
3623: *
3624: * Return pointer to new ospf_packet
3625: * NULL if we can not allocate, eg because LSA is bigger than imposed limit
3626: * on packet sizes (in which case offending LSA is deleted from update list)
3627: */
3628: static struct ospf_packet *
3629: ospf_ls_upd_packet_new (struct list *update, struct ospf_interface *oi)
3630: {
3631: struct ospf_lsa *lsa;
3632: struct listnode *ln;
3633: size_t size;
3634: static char warned = 0;
3635:
3636: lsa = listgetdata((ln = listhead (update)));
3637: assert (lsa->data);
3638:
3639: if ((OSPF_LS_UPD_MIN_SIZE + ntohs (lsa->data->length))
3640: > ospf_packet_max (oi))
3641: {
3642: if (!warned)
3643: {
3644: zlog_warn ("ospf_ls_upd_packet_new: oversized LSA encountered!"
3645: "will need to fragment. Not optimal. Try divide up"
3646: " your network with areas. Use 'debug ospf packet send'"
3647: " to see details, or look at 'show ip ospf database ..'");
3648: warned = 1;
3649: }
3650:
3651: if (IS_DEBUG_OSPF_PACKET (0, SEND))
3652: zlog_debug ("ospf_ls_upd_packet_new: oversized LSA id:%s,"
3653: " %d bytes originated by %s, will be fragmented!",
3654: inet_ntoa (lsa->data->id),
3655: ntohs (lsa->data->length),
3656: inet_ntoa (lsa->data->adv_router));
3657:
3658: /*
3659: * Allocate just enough to fit this LSA only, to avoid including other
3660: * LSAs in fragmented LSA Updates.
3661: */
3662: size = ntohs (lsa->data->length) + (oi->ifp->mtu - ospf_packet_max (oi))
3663: + OSPF_LS_UPD_MIN_SIZE;
3664: }
3665: else
3666: size = oi->ifp->mtu;
3667:
3668: if (size > OSPF_MAX_PACKET_SIZE)
3669: {
3670: zlog_warn ("ospf_ls_upd_packet_new: oversized LSA id:%s too big,"
3671: " %d bytes, packet size %ld, dropping it completely."
3672: " OSPF routing is broken!",
3673: inet_ntoa (lsa->data->id), ntohs (lsa->data->length),
3674: (long int) size);
3675: list_delete_node (update, ln);
3676: return NULL;
3677: }
3678:
3679: /* IP header is built up separately by ospf_write(). This means, that we must
3680: * reduce the "affordable" size just calculated by length of an IP header.
3681: * This makes sure, that even if we manage to fill the payload with LSA data
3682: * completely, the final packet (our data plus IP header) still fits into
3683: * outgoing interface MTU. This correction isn't really meaningful for an
3684: * oversized LSA, but for consistency the correction is done for both cases.
3685: *
3686: * P.S. OSPF_MAX_PACKET_SIZE above already includes IP header size
3687: */
3688: return ospf_packet_new (size - sizeof (struct ip));
3689: }
3690:
3691: static void
3692: ospf_ls_upd_queue_send (struct ospf_interface *oi, struct list *update,
3693: struct in_addr addr)
3694: {
3695: struct ospf_packet *op;
3696: u_int16_t length = OSPF_HEADER_SIZE;
3697:
3698: if (IS_DEBUG_OSPF_EVENT)
3699: zlog_debug ("listcount = %d, dst %s", listcount (update), inet_ntoa(addr));
3700:
3701: op = ospf_ls_upd_packet_new (update, oi);
3702:
3703: /* Prepare OSPF common header. */
3704: ospf_make_header (OSPF_MSG_LS_UPD, oi, op->s);
3705:
3706: /* Prepare OSPF Link State Update body.
3707: * Includes Type-7 translation.
3708: */
3709: length += ospf_make_ls_upd (oi, update, op->s);
3710:
3711: /* Fill OSPF header. */
3712: ospf_fill_header (oi, op->s, length);
3713:
3714: /* Set packet length. */
3715: op->length = length;
3716:
3717: /* Decide destination address. */
3718: if (oi->type == OSPF_IFTYPE_POINTOPOINT)
3719: op->dst.s_addr = htonl (OSPF_ALLSPFROUTERS);
3720: else
3721: op->dst.s_addr = addr.s_addr;
3722:
3723: /* Add packet to the interface output queue. */
3724: ospf_packet_add (oi, op);
3725:
3726: /* Hook thread to write packet. */
3727: OSPF_ISM_WRITE_ON (oi->ospf);
3728: }
3729:
3730: static int
3731: ospf_ls_upd_send_queue_event (struct thread *thread)
3732: {
3733: struct ospf_interface *oi = THREAD_ARG(thread);
3734: struct route_node *rn;
3735: struct route_node *rnext;
3736: struct list *update;
3737: char again = 0;
3738:
3739: oi->t_ls_upd_event = NULL;
3740:
3741: if (IS_DEBUG_OSPF_EVENT)
3742: zlog_debug ("ospf_ls_upd_send_queue start");
3743:
3744: for (rn = route_top (oi->ls_upd_queue); rn; rn = rnext)
3745: {
3746: rnext = route_next (rn);
3747:
3748: if (rn->info == NULL)
3749: continue;
3750:
3751: update = (struct list *)rn->info;
3752:
3753: ospf_ls_upd_queue_send (oi, update, rn->p.u.prefix4);
3754:
3755: /* list might not be empty. */
3756: if (listcount(update) == 0)
3757: {
3758: list_delete (rn->info);
3759: rn->info = NULL;
3760: route_unlock_node (rn);
3761: }
3762: else
3763: again = 1;
3764: }
3765:
3766: if (again != 0)
3767: {
3768: if (IS_DEBUG_OSPF_EVENT)
3769: zlog_debug ("ospf_ls_upd_send_queue: update lists not cleared,"
3770: " %d nodes to try again, raising new event", again);
3771: oi->t_ls_upd_event =
3772: thread_add_event (master, ospf_ls_upd_send_queue_event, oi, 0);
3773: }
3774:
3775: if (IS_DEBUG_OSPF_EVENT)
3776: zlog_debug ("ospf_ls_upd_send_queue stop");
3777:
3778: return 0;
3779: }
3780:
3781: void
3782: ospf_ls_upd_send (struct ospf_neighbor *nbr, struct list *update, int flag)
3783: {
3784: struct ospf_interface *oi;
3785: struct ospf_lsa *lsa;
3786: struct prefix_ipv4 p;
3787: struct route_node *rn;
3788: struct listnode *node;
3789:
3790: oi = nbr->oi;
3791:
3792: p.family = AF_INET;
3793: p.prefixlen = IPV4_MAX_BITLEN;
3794:
3795: /* Decide destination address. */
3796: if (oi->type == OSPF_IFTYPE_VIRTUALLINK)
3797: p.prefix = oi->vl_data->peer_addr;
3798: else if (oi->type == OSPF_IFTYPE_POINTOPOINT)
3799: p.prefix.s_addr = htonl (OSPF_ALLSPFROUTERS);
3800: else if (flag == OSPF_SEND_PACKET_DIRECT)
3801: p.prefix = nbr->address.u.prefix4;
3802: else if (oi->state == ISM_DR || oi->state == ISM_Backup)
3803: p.prefix.s_addr = htonl (OSPF_ALLSPFROUTERS);
3804: else if (oi->type == OSPF_IFTYPE_POINTOMULTIPOINT)
3805: p.prefix.s_addr = htonl (OSPF_ALLSPFROUTERS);
3806: else
3807: p.prefix.s_addr = htonl (OSPF_ALLDROUTERS);
3808:
3809: if (oi->type == OSPF_IFTYPE_NBMA)
3810: {
3811: if (flag == OSPF_SEND_PACKET_INDIRECT)
3812: zlog_warn ("* LS-Update is directly sent on NBMA network.");
3813: if (IPV4_ADDR_SAME(&oi->address->u.prefix4, &p.prefix.s_addr))
3814: zlog_warn ("* LS-Update is sent to myself.");
3815: }
3816:
3817: rn = route_node_get (oi->ls_upd_queue, (struct prefix *) &p);
3818:
3819: if (rn->info == NULL)
3820: rn->info = list_new ();
3821:
3822: for (ALL_LIST_ELEMENTS_RO (update, node, lsa))
3823: listnode_add (rn->info, ospf_lsa_lock (lsa)); /* oi->ls_upd_queue */
3824:
3825: if (oi->t_ls_upd_event == NULL)
3826: oi->t_ls_upd_event =
3827: thread_add_event (master, ospf_ls_upd_send_queue_event, oi, 0);
3828: }
3829:
3830: static void
3831: ospf_ls_ack_send_list (struct ospf_interface *oi, struct list *ack,
3832: struct in_addr dst)
3833: {
3834: struct ospf_packet *op;
3835: u_int16_t length = OSPF_HEADER_SIZE;
3836:
3837: op = ospf_packet_new (oi->ifp->mtu);
3838:
3839: /* Prepare OSPF common header. */
3840: ospf_make_header (OSPF_MSG_LS_ACK, oi, op->s);
3841:
3842: /* Prepare OSPF Link State Acknowledgment body. */
3843: length += ospf_make_ls_ack (oi, ack, op->s);
3844:
3845: /* Fill OSPF header. */
3846: ospf_fill_header (oi, op->s, length);
3847:
3848: /* Set packet length. */
3849: op->length = length;
3850:
3851: /* Set destination IP address. */
3852: op->dst = dst;
3853:
3854: /* Add packet to the interface output queue. */
3855: ospf_packet_add (oi, op);
3856:
3857: /* Hook thread to write packet. */
3858: OSPF_ISM_WRITE_ON (oi->ospf);
3859: }
3860:
3861: static int
3862: ospf_ls_ack_send_event (struct thread *thread)
3863: {
3864: struct ospf_interface *oi = THREAD_ARG (thread);
3865:
3866: oi->t_ls_ack_direct = NULL;
3867:
3868: while (listcount (oi->ls_ack_direct.ls_ack))
3869: ospf_ls_ack_send_list (oi, oi->ls_ack_direct.ls_ack,
3870: oi->ls_ack_direct.dst);
3871:
3872: return 0;
3873: }
3874:
3875: void
3876: ospf_ls_ack_send (struct ospf_neighbor *nbr, struct ospf_lsa *lsa)
3877: {
3878: struct ospf_interface *oi = nbr->oi;
3879:
3880: if (listcount (oi->ls_ack_direct.ls_ack) == 0)
3881: oi->ls_ack_direct.dst = nbr->address.u.prefix4;
3882:
3883: listnode_add (oi->ls_ack_direct.ls_ack, ospf_lsa_lock (lsa));
3884:
3885: if (oi->t_ls_ack_direct == NULL)
3886: oi->t_ls_ack_direct =
3887: thread_add_event (master, ospf_ls_ack_send_event, oi, 0);
3888: }
3889:
3890: /* Send Link State Acknowledgment delayed. */
3891: void
3892: ospf_ls_ack_send_delayed (struct ospf_interface *oi)
3893: {
3894: struct in_addr dst;
3895:
3896: /* Decide destination address. */
3897: /* RFC2328 Section 13.5 On non-broadcast
3898: networks, delayed Link State Acknowledgment packets must be
3899: unicast separately over each adjacency (i.e., neighbor whose
3900: state is >= Exchange). */
3901: if (oi->type == OSPF_IFTYPE_NBMA)
3902: {
3903: struct ospf_neighbor *nbr;
3904: struct route_node *rn;
3905:
3906: for (rn = route_top (oi->nbrs); rn; rn = route_next (rn))
3907: if ((nbr = rn->info) != NULL)
3908: if (nbr != oi->nbr_self && nbr->state >= NSM_Exchange)
3909: while (listcount (oi->ls_ack))
3910: ospf_ls_ack_send_list (oi, oi->ls_ack, nbr->address.u.prefix4);
3911: return;
3912: }
3913: if (oi->type == OSPF_IFTYPE_VIRTUALLINK)
3914: dst.s_addr = oi->vl_data->peer_addr.s_addr;
3915: else if (oi->state == ISM_DR || oi->state == ISM_Backup)
3916: dst.s_addr = htonl (OSPF_ALLSPFROUTERS);
3917: else if (oi->type == OSPF_IFTYPE_POINTOPOINT)
3918: dst.s_addr = htonl (OSPF_ALLSPFROUTERS);
3919: else if (oi->type == OSPF_IFTYPE_POINTOMULTIPOINT)
3920: dst.s_addr = htonl (OSPF_ALLSPFROUTERS);
3921: else
3922: dst.s_addr = htonl (OSPF_ALLDROUTERS);
3923:
3924: while (listcount (oi->ls_ack))
3925: ospf_ls_ack_send_list (oi, oi->ls_ack, dst);
3926: }
FreeBSD-CVSweb <freebsd-cvsweb@FreeBSD.org>