]> git.proxmox.com Git - mirror_frr.git/blame - ospfd/ospf_lsa.c
*: manual SPDX License ID conversions
[mirror_frr.git] / ospfd / ospf_lsa.c
CommitLineData
718e3744 1/*
2 * OSPF Link State Advertisement
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 *
896014f4
DL
17 * You should have received a copy of the GNU General Public License along
18 * with this program; see the file COPYING; if not, write to the Free Software
19 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
718e3744 20 */
21
22#include <zebra.h>
23
cbf3e3eb 24#include "monotime.h"
718e3744 25#include "linklist.h"
26#include "prefix.h"
27#include "if.h"
28#include "table.h"
29#include "memory.h"
30#include "stream.h"
31#include "log.h"
32#include "thread.h"
33#include "hash.h"
d62a17ae 34#include "sockunion.h" /* for inet_aton() */
6a270cd9 35#include "checksum.h"
5920b3eb 36#include "network.h"
718e3744 37
38#include "ospfd/ospfd.h"
39#include "ospfd/ospf_interface.h"
40#include "ospfd/ospf_ism.h"
41#include "ospfd/ospf_asbr.h"
42#include "ospfd/ospf_lsa.h"
43#include "ospfd/ospf_lsdb.h"
44#include "ospfd/ospf_neighbor.h"
45#include "ospfd/ospf_nsm.h"
46#include "ospfd/ospf_flood.h"
47#include "ospfd/ospf_packet.h"
48#include "ospfd/ospf_spf.h"
49#include "ospfd/ospf_dump.h"
50#include "ospfd/ospf_route.h"
51#include "ospfd/ospf_ase.h"
52#include "ospfd/ospf_zebra.h"
493472ba 53#include "ospfd/ospf_abr.h"
542a208f 54#include "ospfd/ospf_errors.h"
6b0655a2 55
a8c22275 56static struct ospf_lsa *ospf_handle_summarylsa_lsId_chg(struct ospf *ospf,
57 struct prefix_ipv4 *p,
58 uint8_t type,
59 uint32_t metric,
60 struct in_addr old_id);
61static struct ospf_lsa *
62ospf_summary_lsa_prepare_and_flood(struct prefix_ipv4 *p, uint32_t metric,
63 struct ospf_area *area, struct in_addr id);
64static struct ospf_lsa *ospf_summary_lsa_refresh(struct ospf *ospf,
65 struct ospf_lsa *lsa);
66static struct ospf_lsa *
67ospf_asbr_summary_lsa_prepare_and_flood(struct prefix_ipv4 *p, uint32_t metric,
68 struct ospf_area *area,
69 struct in_addr id);
70static struct ospf_lsa *ospf_summary_asbr_lsa_refresh(struct ospf *ospf,
71 struct ospf_lsa *lsa);
72static struct ospf_lsa *ospf_handle_exnl_lsa_lsId_chg(struct ospf *ospf,
73 struct external_info *ei,
74 struct in_addr id);
75static struct ospf_lsa *
76ospf_exnl_lsa_prepare_and_flood(struct ospf *ospf, struct external_info *ei,
77 struct in_addr id);
78
d7c0a89a 79uint32_t get_metric(uint8_t *metric)
718e3744 80{
d7c0a89a 81 uint32_t m;
d62a17ae 82 m = metric[0];
83 m = (m << 8) + metric[1];
84 m = (m << 8) + metric[2];
85 return m;
718e3744 86}
87
6b0655a2 88
d62a17ae 89struct timeval int2tv(int a)
b6927875 90{
d62a17ae 91 struct timeval ret;
b6927875 92
d62a17ae 93 ret.tv_sec = a;
94 ret.tv_usec = 0;
b6927875 95
d62a17ae 96 return ret;
b6927875
DS
97}
98
d62a17ae 99struct timeval msec2tv(int a)
718e3744 100{
d62a17ae 101 struct timeval ret;
718e3744 102
d62a17ae 103 ret.tv_sec = a / 1000;
104 ret.tv_usec = (a % 1000) * 1000;
718e3744 105
d62a17ae 106 return ret;
718e3744 107}
108
d62a17ae 109int ospf_lsa_refresh_delay(struct ospf_lsa *lsa)
718e3744 110{
d62a17ae 111 struct timeval delta;
112 int delay = 0;
718e3744 113
d62a17ae 114 if (monotime_since(&lsa->tv_orig, &delta)
115 < OSPF_MIN_LS_INTERVAL * 1000LL) {
116 struct timeval minv = msec2tv(OSPF_MIN_LS_INTERVAL);
117 timersub(&minv, &delta, &minv);
cbf3e3eb 118
d62a17ae 119 /* TBD: remove padding to full sec, return timeval instead */
120 delay = minv.tv_sec + !!minv.tv_usec;
718e3744 121
d62a17ae 122 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
123 zlog_debug(
96b663a3
MS
124 "LSA[Type%d:%pI4]: Refresh timer delay %d seconds",
125 lsa->data->type, &lsa->data->id,
d62a17ae 126 delay);
718e3744 127
d62a17ae 128 assert(delay > 0);
129 }
718e3744 130
d62a17ae 131 return delay;
718e3744 132}
133
6b0655a2 134
d62a17ae 135int get_age(struct ospf_lsa *lsa)
718e3744 136{
d62a17ae 137 struct timeval rel;
718e3744 138
d62a17ae 139 monotime_since(&lsa->tv_recv, &rel);
140 return ntohs(lsa->data->ls_age) + rel.tv_sec;
718e3744 141}
142
6b0655a2 143
718e3744 144/* Fletcher Checksum -- Refer to RFC1008. */
718e3744 145
d62a17ae 146/* All the offsets are zero-based. The offsets in the RFC1008 are
6a270cd9 147 one-based. */
d7c0a89a 148uint16_t ospf_lsa_checksum(struct lsa_header *lsa)
718e3744 149{
c4efd0f4 150 uint8_t *buffer = &lsa->options;
d7c0a89a 151 int options_offset = buffer - (uint8_t *)&lsa->ls_age; /* should be 2 */
718e3744 152
d62a17ae 153 /* Skip the AGE field */
d7c0a89a 154 uint16_t len = ntohs(lsa->length) - options_offset;
718e3744 155
d62a17ae 156 /* Checksum offset starts from "options" field, not the beginning of the
157 lsa_header struct. The offset is 14, rather than 16. */
d7c0a89a 158 int checksum_offset = (uint8_t *)&lsa->checksum - buffer;
718e3744 159
d62a17ae 160 return fletcher_checksum(buffer, len, checksum_offset);
718e3744 161}
162
d62a17ae 163int ospf_lsa_checksum_valid(struct lsa_header *lsa)
d8a4e42b 164{
c4efd0f4 165 uint8_t *buffer = &lsa->options;
d7c0a89a 166 int options_offset = buffer - (uint8_t *)&lsa->ls_age; /* should be 2 */
d8a4e42b 167
d62a17ae 168 /* Skip the AGE field */
d7c0a89a 169 uint16_t len = ntohs(lsa->length) - options_offset;
d8a4e42b 170
d62a17ae 171 return (fletcher_checksum(buffer, len, FLETCHER_CHECKSUM_VALIDATE)
172 == 0);
d8a4e42b
JR
173}
174
718e3744 175
718e3744 176/* Create OSPF LSA. */
4d762f26 177struct ospf_lsa *ospf_lsa_new(void)
718e3744 178{
d62a17ae 179 struct ospf_lsa *new;
718e3744 180
d62a17ae 181 new = XCALLOC(MTYPE_OSPF_LSA, sizeof(struct ospf_lsa));
718e3744 182
d62a17ae 183 new->flags = 0;
184 new->lock = 1;
185 new->retransmit_counter = 0;
186 monotime(&new->tv_recv);
187 new->tv_orig = new->tv_recv;
188 new->refresh_list = -1;
b5a8894d 189 new->vrf_id = VRF_DEFAULT;
df074ec3 190 new->to_be_acknowledged = 0;
2f30cb25 191 new->opaque_zero_len_delete = 0;
d62a17ae 192
193 return new;
718e3744 194}
195
5b3d4186
DS
196struct ospf_lsa *ospf_lsa_new_and_data(size_t size)
197{
198 struct ospf_lsa *new;
199
200 new = ospf_lsa_new();
201 new->data = ospf_lsa_data_new(size);
8db278b5 202 new->size = size;
5b3d4186
DS
203
204 return new;
205}
206
718e3744 207/* Duplicate OSPF LSA. */
d62a17ae 208struct ospf_lsa *ospf_lsa_dup(struct ospf_lsa *lsa)
718e3744 209{
d62a17ae 210 struct ospf_lsa *new;
718e3744 211
d62a17ae 212 if (lsa == NULL)
213 return NULL;
718e3744 214
d62a17ae 215 new = XCALLOC(MTYPE_OSPF_LSA, sizeof(struct ospf_lsa));
718e3744 216
d62a17ae 217 memcpy(new, lsa, sizeof(struct ospf_lsa));
218 UNSET_FLAG(new->flags, OSPF_LSA_DISCARD);
219 new->lock = 1;
220 new->retransmit_counter = 0;
221 new->data = ospf_lsa_data_dup(lsa->data);
718e3744 222
d62a17ae 223 /* kevinm: Clear the refresh_list, otherwise there are going
224 to be problems when we try to remove the LSA from the
225 queue (which it's not a member of.)
226 XXX: Should we add the LSA to the refresh_list queue? */
227 new->refresh_list = -1;
f2c80652 228
d62a17ae 229 if (IS_DEBUG_OSPF(lsa, LSA))
230 zlog_debug("LSA: duplicated %p (new: %p)", (void *)lsa,
231 (void *)new);
f2c80652 232
d62a17ae 233 return new;
718e3744 234}
235
236/* Free OSPF LSA. */
d62a17ae 237void ospf_lsa_free(struct ospf_lsa *lsa)
718e3744 238{
d62a17ae 239 assert(lsa->lock == 0);
240
241 if (IS_DEBUG_OSPF(lsa, LSA))
242 zlog_debug("LSA: freed %p", (void *)lsa);
718e3744 243
d62a17ae 244 /* Delete LSA data. */
245 if (lsa->data != NULL)
246 ospf_lsa_data_free(lsa->data);
718e3744 247
d62a17ae 248 assert(lsa->refresh_list < 0);
718e3744 249
d62a17ae 250 memset(lsa, 0, sizeof(struct ospf_lsa));
251 XFREE(MTYPE_OSPF_LSA, lsa);
718e3744 252}
253
254/* Lock LSA. */
d62a17ae 255struct ospf_lsa *ospf_lsa_lock(struct ospf_lsa *lsa)
718e3744 256{
d62a17ae 257 lsa->lock++;
258 return lsa;
718e3744 259}
260
261/* Unlock LSA. */
d62a17ae 262void ospf_lsa_unlock(struct ospf_lsa **lsa)
718e3744 263{
d62a17ae 264 /* This is sanity check. */
265 if (!lsa || !*lsa)
266 return;
718e3744 267
d62a17ae 268 (*lsa)->lock--;
718e3744 269
d62a17ae 270 assert((*lsa)->lock >= 0);
271
272 if ((*lsa)->lock == 0) {
273 assert(CHECK_FLAG((*lsa)->flags, OSPF_LSA_DISCARD));
274 ospf_lsa_free(*lsa);
275 *lsa = NULL;
276 }
718e3744 277}
278
279/* Check discard flag. */
d62a17ae 280void ospf_lsa_discard(struct ospf_lsa *lsa)
718e3744 281{
d62a17ae 282 if (!CHECK_FLAG(lsa->flags, OSPF_LSA_DISCARD)) {
283 SET_FLAG(lsa->flags, OSPF_LSA_DISCARD);
284 ospf_lsa_unlock(&lsa);
285 }
718e3744 286}
287
288/* Create LSA data. */
d62a17ae 289struct lsa_header *ospf_lsa_data_new(size_t size)
718e3744 290{
d62a17ae 291 return XCALLOC(MTYPE_OSPF_LSA_DATA, size);
718e3744 292}
293
294/* Duplicate LSA data. */
d62a17ae 295struct lsa_header *ospf_lsa_data_dup(struct lsa_header *lsah)
718e3744 296{
d62a17ae 297 struct lsa_header *new;
718e3744 298
d62a17ae 299 new = ospf_lsa_data_new(ntohs(lsah->length));
300 memcpy(new, lsah, ntohs(lsah->length));
718e3744 301
d62a17ae 302 return new;
718e3744 303}
304
305/* Free LSA data. */
d62a17ae 306void ospf_lsa_data_free(struct lsa_header *lsah)
718e3744 307{
d62a17ae 308 if (IS_DEBUG_OSPF(lsa, LSA))
96b663a3
MS
309 zlog_debug("LSA[Type%d:%pI4]: data freed %p", lsah->type,
310 &lsah->id, (void *)lsah);
718e3744 311
d62a17ae 312 XFREE(MTYPE_OSPF_LSA_DATA, lsah);
718e3744 313}
314
6b0655a2 315
718e3744 316/* LSA general functions. */
317
d62a17ae 318const char *dump_lsa_key(struct ospf_lsa *lsa)
718e3744 319{
2b64873d 320 static char buf[sizeof("Type255,id(255.255.255.255),ar(255.255.255.255)")+1];
d62a17ae 321 struct lsa_header *lsah;
718e3744 322
d62a17ae 323 if (lsa != NULL && (lsah = lsa->data) != NULL) {
324 char id[INET_ADDRSTRLEN], ar[INET_ADDRSTRLEN];
96b663a3
MS
325 inet_ntop(AF_INET, &lsah->id, id, sizeof(id));
326 inet_ntop(AF_INET, &lsah->adv_router, ar, sizeof(ar));
718e3744 327
772270f3
QY
328 snprintf(buf, sizeof(buf), "Type%d,id(%s),ar(%s)", lsah->type,
329 id, ar);
d62a17ae 330 } else
a1d6bbb1 331 strlcpy(buf, "NULL", sizeof(buf));
718e3744 332
d62a17ae 333 return buf;
718e3744 334}
335
d7c0a89a 336uint32_t lsa_seqnum_increment(struct ospf_lsa *lsa)
718e3744 337{
d7c0a89a 338 uint32_t seqnum;
718e3744 339
d62a17ae 340 seqnum = ntohl(lsa->data->ls_seqnum) + 1;
718e3744 341
d62a17ae 342 return htonl(seqnum);
718e3744 343}
344
d7c0a89a 345void lsa_header_set(struct stream *s, uint8_t options, uint8_t type,
d62a17ae 346 struct in_addr id, struct in_addr router_id)
718e3744 347{
d62a17ae 348 struct lsa_header *lsah;
718e3744 349
d62a17ae 350 lsah = (struct lsa_header *)STREAM_DATA(s);
718e3744 351
d62a17ae 352 lsah->ls_age = htons(OSPF_LSA_INITIAL_AGE);
353 lsah->options = options;
354 lsah->type = type;
355 lsah->id = id;
356 lsah->adv_router = router_id;
357 lsah->ls_seqnum = htonl(OSPF_INITIAL_SEQUENCE_NUMBER);
718e3744 358
d62a17ae 359 stream_forward_endp(s, OSPF_LSA_HEADER_SIZE);
718e3744 360}
6b0655a2 361
68980084 362
718e3744 363/* router-LSA related functions. */
364/* Get router-LSA flags. */
7fd0729f 365uint8_t router_lsa_flags(struct ospf_area *area)
d62a17ae 366{
d7c0a89a 367 uint8_t flags;
d62a17ae 368
369 flags = area->ospf->flags;
370
371 /* Set virtual link flag. */
372 if (ospf_full_virtual_nbrs(area))
373 SET_FLAG(flags, ROUTER_LSA_VIRTUAL);
374 else
375 /* Just sanity check */
376 UNSET_FLAG(flags, ROUTER_LSA_VIRTUAL);
377
378 /* Set Shortcut ABR behabiour flag. */
379 UNSET_FLAG(flags, ROUTER_LSA_SHORTCUT);
380 if (area->ospf->abr_type == OSPF_ABR_SHORTCUT)
381 if (!OSPF_IS_AREA_BACKBONE(area))
382 if ((area->shortcut_configured == OSPF_SHORTCUT_DEFAULT
383 && area->ospf->backbone == NULL)
384 || area->shortcut_configured
385 == OSPF_SHORTCUT_ENABLE)
386 SET_FLAG(flags, ROUTER_LSA_SHORTCUT);
387
388 /* ASBR can't exit in stub area. */
389 if (area->external_routing == OSPF_AREA_STUB)
390 UNSET_FLAG(flags, ROUTER_LSA_EXTERNAL);
391 /* If ASBR set External flag */
392 else if (IS_OSPF_ASBR(area->ospf))
393 SET_FLAG(flags, ROUTER_LSA_EXTERNAL);
394
395 /* Set ABR dependent flags */
396 if (IS_OSPF_ABR(area->ospf)) {
397 SET_FLAG(flags, ROUTER_LSA_BORDER);
398 /* If Area is NSSA and we are both ABR and unconditional
399 * translator,
400 * set Nt bit to inform other routers.
401 */
402 if ((area->external_routing == OSPF_AREA_NSSA)
403 && (area->NSSATranslatorRole == OSPF_NSSA_ROLE_ALWAYS))
404 SET_FLAG(flags, ROUTER_LSA_NT);
405 }
406 return flags;
718e3744 407}
408
409/* Lookup neighbor other than myself.
410 And check neighbor count,
411 Point-to-Point link must have only 1 neighbor. */
d62a17ae 412struct ospf_neighbor *ospf_nbr_lookup_ptop(struct ospf_interface *oi)
718e3744 413{
d62a17ae 414 struct ospf_neighbor *nbr = NULL;
415 struct route_node *rn;
718e3744 416
d62a17ae 417 /* Search neighbor, there must be one of two nbrs. */
418 for (rn = route_top(oi->nbrs); rn; rn = route_next(rn))
419 if ((nbr = rn->info))
420 if (!IPV4_ADDR_SAME(&nbr->router_id,
421 &oi->ospf->router_id))
422 if (nbr->state == NSM_Full) {
423 route_unlock_node(rn);
424 break;
425 }
718e3744 426
d62a17ae 427 /* PtoP link must have only 1 neighbor. */
428 if (ospf_nbr_count(oi, 0) > 1)
bf8d8a54
JAG
429 flog_warn(
430 EC_OSPF_PTP_NEIGHBOR,
431 "Point-to-Point link on interface %s has more than 1 neighbor.",
432 oi->ifp->name);
718e3744 433
d62a17ae 434 return nbr;
718e3744 435}
436
88d6cf37 437/* Determine cost of link, taking RFC3137 stub-router support into
438 * consideration
439 */
d7c0a89a 440static uint16_t ospf_link_cost(struct ospf_interface *oi)
88d6cf37 441{
d62a17ae 442 /* RFC3137 stub router support */
443 if (!CHECK_FLAG(oi->area->stub_router_state, OSPF_AREA_IS_STUB_ROUTED))
444 return oi->output_cost;
445 else
446 return OSPF_OUTPUT_COST_INFINITE;
88d6cf37 447}
448
718e3744 449/* Set a link information. */
7fd0729f
G
450char link_info_set(struct stream **s, struct in_addr id, struct in_addr data,
451 uint8_t type, uint8_t tos, uint16_t cost)
d62a17ae 452{
453 /* LSA stream is initially allocated to OSPF_MAX_LSA_SIZE, suits
454 * vast majority of cases. Some rare routers with lots of links need
455 * more.
f5267398 456 * we try accommodate those here.
d62a17ae 457 */
db3c830a 458 if (STREAM_WRITEABLE(*s) < OSPF_ROUTER_LSA_LINK_SIZE) {
d62a17ae 459 size_t ret = OSPF_MAX_LSA_SIZE;
460
461 /* Can we enlarge the stream still? */
db3c830a 462 if (STREAM_SIZE(*s) == OSPF_MAX_LSA_SIZE) {
d62a17ae 463 /* we futz the size here for simplicity, really we need
464 * to account
465 * for just:
0d6f7fd6 466 * IP Header - (sizeof(struct ip))
d62a17ae 467 * OSPF Header - OSPF_HEADER_SIZE
468 * LSA Header - OSPF_LSA_HEADER_SIZE
469 * MD5 auth data, if MD5 is configured -
470 * OSPF_AUTH_MD5_SIZE.
471 *
472 * Simpler just to subtract OSPF_MAX_LSA_SIZE though.
473 */
db3c830a 474 ret = stream_resize_inplace(
9d303b37 475 s, OSPF_MAX_PACKET_SIZE - OSPF_MAX_LSA_SIZE);
d62a17ae 476 }
477
478 if (ret == OSPF_MAX_LSA_SIZE) {
13ab4921 479 flog_warn(
cf444bcf 480 EC_OSPF_LSA_SIZE,
d62a17ae 481 "%s: Out of space in LSA stream, left %zd, size %zd",
db3c830a
DS
482 __func__, STREAM_WRITEABLE(*s),
483 STREAM_SIZE(*s));
d62a17ae 484 return 0;
485 }
486 }
487
488 /* TOS based routing is not supported. */
db3c830a
DS
489 stream_put_ipv4(*s, id.s_addr); /* Link ID. */
490 stream_put_ipv4(*s, data.s_addr); /* Link Data. */
491 stream_putc(*s, type); /* Link Type. */
492 stream_putc(*s, tos); /* TOS = 0. */
493 stream_putw(*s, cost); /* Link Cost. */
d62a17ae 494
495 return 1;
718e3744 496}
497
e4529636 498/* Describe Point-to-Point link (Section 12.4.1.1). */
bc97889b
AL
499
500/* Note: If the interface is configured as point-to-point dmvpn then the other
501 * end of link is dmvpn hub with point-to-multipoint ospf network type. The
502 * hub then expects this router to populate the stub network and also Link Data
503 * Field set to IP Address and not MIB-II ifIndex
504 */
db3c830a 505static int lsa_link_ptop_set(struct stream **s, struct ospf_interface *oi)
d62a17ae 506{
507 int links = 0;
508 struct ospf_neighbor *nbr;
509 struct in_addr id, mask, data;
d7c0a89a 510 uint16_t cost = ospf_link_cost(oi);
d62a17ae 511
512 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
513 zlog_debug("LSA[Type1]: Set link Point-to-Point");
514
515 if ((nbr = ospf_nbr_lookup_ptop(oi)))
516 if (nbr->state == NSM_Full) {
517 if (CHECK_FLAG(oi->connected->flags,
bc97889b
AL
518 ZEBRA_IFA_UNNUMBERED)
519 && !oi->ptp_dmvpn) {
d62a17ae 520 /* For unnumbered point-to-point networks, the
521 Link Data field
522 should specify the interface's MIB-II ifIndex
523 value. */
524 data.s_addr = htonl(oi->ifp->ifindex);
525 links += link_info_set(
526 s, nbr->router_id, data,
527 LSA_LINK_TYPE_POINTOPOINT, 0, cost);
528 } else {
529 links += link_info_set(
530 s, nbr->router_id,
531 oi->address->u.prefix4,
532 LSA_LINK_TYPE_POINTOPOINT, 0, cost);
533 }
534 }
535
536 /* no need for a stub link for unnumbered interfaces */
bc97889b
AL
537 if (oi->ptp_dmvpn
538 || !CHECK_FLAG(oi->connected->flags, ZEBRA_IFA_UNNUMBERED)) {
d62a17ae 539 /* Regardless of the state of the neighboring router, we must
540 add a Type 3 link (stub network).
541 N.B. Options 1 & 2 share basically the same logic. */
542 masklen2ip(oi->address->prefixlen, &mask);
543 id.s_addr = CONNECTED_PREFIX(oi->connected)->u.prefix4.s_addr
544 & mask.s_addr;
545 links += link_info_set(s, id, mask, LSA_LINK_TYPE_STUB, 0,
546 oi->output_cost);
547 }
548
549 return links;
718e3744 550}
551
552/* Describe Broadcast Link. */
db3c830a 553static int lsa_link_broadcast_set(struct stream **s, struct ospf_interface *oi)
d62a17ae 554{
555 struct ospf_neighbor *dr;
556 struct in_addr id, mask;
d7c0a89a 557 uint16_t cost = ospf_link_cost(oi);
d62a17ae 558
559 /* Describe Type 3 Link. */
560 if (oi->state == ISM_Waiting) {
561 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
562 zlog_debug(
3efd0893 563 "LSA[Type1]: Interface %s is in state Waiting. Adding stub interface",
d62a17ae 564 oi->ifp->name);
565 masklen2ip(oi->address->prefixlen, &mask);
566 id.s_addr = oi->address->u.prefix4.s_addr & mask.s_addr;
567 return link_info_set(s, id, mask, LSA_LINK_TYPE_STUB, 0,
568 oi->output_cost);
569 }
570
571 dr = ospf_nbr_lookup_by_addr(oi->nbrs, &DR(oi));
572 /* Describe Type 2 link. */
9d303b37
DL
573 if (dr && (dr->state == NSM_Full
574 || IPV4_ADDR_SAME(&oi->address->u.prefix4, &DR(oi)))
d62a17ae 575 && ospf_nbr_count(oi, NSM_Full) > 0) {
576 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
577 zlog_debug(
3efd0893 578 "LSA[Type1]: Interface %s has a DR. Adding transit interface",
d62a17ae 579 oi->ifp->name);
580 return link_info_set(s, DR(oi), oi->address->u.prefix4,
581 LSA_LINK_TYPE_TRANSIT, 0, cost);
582 }
583 /* Describe type 3 link. */
584 else {
585 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
586 zlog_debug(
3efd0893 587 "LSA[Type1]: Interface %s has no DR. Adding stub interface",
d62a17ae 588 oi->ifp->name);
589 masklen2ip(oi->address->prefixlen, &mask);
590 id.s_addr = oi->address->u.prefix4.s_addr & mask.s_addr;
591 return link_info_set(s, id, mask, LSA_LINK_TYPE_STUB, 0,
592 oi->output_cost);
593 }
594}
595
db3c830a 596static int lsa_link_loopback_set(struct stream **s, struct ospf_interface *oi)
d62a17ae 597{
598 struct in_addr id, mask;
599
600 /* Describe Type 3 Link. */
601 if (oi->state != ISM_Loopback)
602 return 0;
603
604 mask.s_addr = 0xffffffff;
605 id.s_addr = oi->address->u.prefix4.s_addr;
606 return link_info_set(s, id, mask, LSA_LINK_TYPE_STUB, 0, 0);
718e3744 607}
608
609/* Describe Virtual Link. */
db3c830a
DS
610static int lsa_link_virtuallink_set(struct stream **s,
611 struct ospf_interface *oi)
718e3744 612{
d62a17ae 613 struct ospf_neighbor *nbr;
d7c0a89a 614 uint16_t cost = ospf_link_cost(oi);
718e3744 615
d62a17ae 616 if (oi->state == ISM_PointToPoint)
617 if ((nbr = ospf_nbr_lookup_ptop(oi)))
618 if (nbr->state == NSM_Full) {
619 return link_info_set(s, nbr->router_id,
620 oi->address->u.prefix4,
621 LSA_LINK_TYPE_VIRTUALLINK,
622 0, cost);
623 }
718e3744 624
d62a17ae 625 return 0;
718e3744 626}
627
628#define lsa_link_nbma_set(S,O) lsa_link_broadcast_set (S, O)
629
d62a17ae 630/* this function add for support point-to-multipoint ,see rfc2328
7afa08da 63112.4.1.4.*/
632/* from "edward rrr" <edward_rrr@hotmail.com>
633 http://marc.theaimsgroup.com/?l=zebra&m=100739222210507&w=2 */
db3c830a 634static int lsa_link_ptomp_set(struct stream **s, struct ospf_interface *oi)
d62a17ae 635{
636 int links = 0;
637 struct route_node *rn;
638 struct ospf_neighbor *nbr = NULL;
639 struct in_addr id, mask;
d7c0a89a 640 uint16_t cost = ospf_link_cost(oi);
d62a17ae 641
642 mask.s_addr = 0xffffffff;
643 id.s_addr = oi->address->u.prefix4.s_addr;
644 links += link_info_set(s, id, mask, LSA_LINK_TYPE_STUB, 0, 0);
645
646 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
647 zlog_debug("PointToMultipoint: running ptomultip_set");
648
649 /* Search neighbor, */
650 for (rn = route_top(oi->nbrs); rn; rn = route_next(rn))
651 if ((nbr = rn->info) != NULL)
652 /* Ignore myself. */
653 if (!IPV4_ADDR_SAME(&nbr->router_id,
654 &oi->ospf->router_id))
655 if (nbr->state == NSM_Full)
656
657 {
658 links += link_info_set(
659 s, nbr->router_id,
660 oi->address->u.prefix4,
661 LSA_LINK_TYPE_POINTOPOINT, 0,
662 cost);
663 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
664 zlog_debug(
96b663a3
MS
665 "PointToMultipoint: set link to %pI4",
666 &oi->address->u.prefix4);
d62a17ae 667 }
668
669 return links;
7afa08da 670}
671
718e3744 672/* Set router-LSA link information. */
db3c830a 673static int router_lsa_link_set(struct stream **s, struct ospf_area *area)
d62a17ae 674{
675 struct listnode *node;
676 struct ospf_interface *oi;
677 int links = 0;
678
679 for (ALL_LIST_ELEMENTS_RO(area->oiflist, node, oi)) {
680 struct interface *ifp = oi->ifp;
681
682 /* Check interface is up, OSPF is enable. */
683 if (if_is_operative(ifp)) {
684 if (oi->state != ISM_Down) {
685 oi->lsa_pos_beg = links;
686 /* Describe each link. */
687 switch (oi->type) {
688 case OSPF_IFTYPE_POINTOPOINT:
689 links += lsa_link_ptop_set(s, oi);
690 break;
691 case OSPF_IFTYPE_BROADCAST:
692 links += lsa_link_broadcast_set(s, oi);
693 break;
694 case OSPF_IFTYPE_NBMA:
695 links += lsa_link_nbma_set(s, oi);
696 break;
697 case OSPF_IFTYPE_POINTOMULTIPOINT:
698 links += lsa_link_ptomp_set(s, oi);
699 break;
700 case OSPF_IFTYPE_VIRTUALLINK:
701 links +=
702 lsa_link_virtuallink_set(s, oi);
703 break;
704 case OSPF_IFTYPE_LOOPBACK:
705 links += lsa_link_loopback_set(s, oi);
706 }
707 oi->lsa_pos_end = links;
708 }
718e3744 709 }
718e3744 710 }
718e3744 711
d62a17ae 712 return links;
718e3744 713}
714
715/* Set router-LSA body. */
7fd0729f 716void ospf_router_lsa_body_set(struct stream **s, struct ospf_area *area)
d62a17ae 717{
718 unsigned long putp;
d7c0a89a 719 uint16_t cnt;
d62a17ae 720
721 /* Set flags. */
db3c830a 722 stream_putc(*s, router_lsa_flags(area));
d62a17ae 723
724 /* Set Zero fields. */
db3c830a 725 stream_putc(*s, 0);
d62a17ae 726
727 /* Keep pointer to # links. */
db3c830a 728 putp = stream_get_endp(*s);
d62a17ae 729
730 /* Forward word */
db3c830a 731 stream_putw(*s, 0);
d62a17ae 732
733 /* Set all link information. */
734 cnt = router_lsa_link_set(s, area);
735
736 /* Set # of links here. */
db3c830a 737 stream_putw_at(*s, putp, cnt);
d62a17ae 738}
739
cc9f21da 740static void ospf_stub_router_timer(struct thread *t)
d62a17ae 741{
742 struct ospf_area *area = THREAD_ARG(t);
743
744 area->t_stub_router = NULL;
745
746 SET_FLAG(area->stub_router_state, OSPF_AREA_WAS_START_STUB_ROUTED);
747
748 /* clear stub route state and generate router-lsa refresh, don't
749 * clobber an administratively set stub-router state though.
750 */
751 if (CHECK_FLAG(area->stub_router_state, OSPF_AREA_ADMIN_STUB_ROUTED))
cc9f21da 752 return;
d62a17ae 753
754 UNSET_FLAG(area->stub_router_state, OSPF_AREA_IS_STUB_ROUTED);
755
756 ospf_router_lsa_update_area(area);
d62a17ae 757}
758
759static void ospf_stub_router_check(struct ospf_area *area)
760{
761 /* area must either be administratively configured to be stub
762 * or startup-time stub-router must be configured and we must in a
763 * pre-stub
764 * state.
765 */
766 if (CHECK_FLAG(area->stub_router_state, OSPF_AREA_ADMIN_STUB_ROUTED)) {
767 SET_FLAG(area->stub_router_state, OSPF_AREA_IS_STUB_ROUTED);
768 return;
769 }
770
771 /* not admin-stubbed, check whether startup stubbing is configured and
772 * whether it's not been done yet
773 */
774 if (CHECK_FLAG(area->stub_router_state,
775 OSPF_AREA_WAS_START_STUB_ROUTED))
776 return;
777
778 if (area->ospf->stub_router_startup_time
779 == OSPF_STUB_ROUTER_UNCONFIGURED) {
780 /* stub-router is hence done forever for this area, even if
781 * someone
782 * tries configure it (take effect next restart).
783 */
784 SET_FLAG(area->stub_router_state,
785 OSPF_AREA_WAS_START_STUB_ROUTED);
786 return;
787 }
788
789 /* startup stub-router configured and not yet done */
790 SET_FLAG(area->stub_router_state, OSPF_AREA_IS_STUB_ROUTED);
791
792 OSPF_AREA_TIMER_ON(area->t_stub_router, ospf_stub_router_timer,
793 area->ospf->stub_router_startup_time);
794}
795
718e3744 796/* Create new router-LSA. */
d62a17ae 797static struct ospf_lsa *ospf_router_lsa_new(struct ospf_area *area)
798{
799 struct ospf *ospf = area->ospf;
800 struct stream *s;
801 struct lsa_header *lsah;
802 struct ospf_lsa *new;
803 int length;
804
805 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
806 zlog_debug("LSA[Type1]: Create router-LSA instance");
807
808 /* check whether stub-router is desired, and if this is the first
809 * router LSA.
810 */
811 ospf_stub_router_check(area);
812
813 /* Create a stream for LSA. */
814 s = stream_new(OSPF_MAX_LSA_SIZE);
815 /* Set LSA common header fields. */
816 lsa_header_set(s, LSA_OPTIONS_GET(area) | LSA_OPTIONS_NSSA_GET(area),
817 OSPF_ROUTER_LSA, ospf->router_id, ospf->router_id);
818
819 /* Set router-LSA body fields. */
db3c830a 820 ospf_router_lsa_body_set(&s, area);
d62a17ae 821
822 /* Set length. */
823 length = stream_get_endp(s);
824 lsah = (struct lsa_header *)STREAM_DATA(s);
825 lsah->length = htons(length);
826
827 /* Now, create OSPF LSA instance. */
5b3d4186 828 new = ospf_lsa_new_and_data(length);
d62a17ae 829
830 new->area = area;
831 SET_FLAG(new->flags, OSPF_LSA_SELF | OSPF_LSA_SELF_CHECKED);
b5a8894d 832 new->vrf_id = area->ospf->vrf_id;
d62a17ae 833
834 /* Copy LSA data to store, discard stream. */
d62a17ae 835 memcpy(new->data, lsah, length);
836 stream_free(s);
837
838 return new;
718e3744 839}
840
841/* Originate Router-LSA. */
d62a17ae 842static struct ospf_lsa *ospf_router_lsa_originate(struct ospf_area *area)
718e3744 843{
d62a17ae 844 struct ospf_lsa *new;
718e3744 845
10514170
RW
846 if (area->ospf->gr_info.restart_in_progress) {
847 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
848 zlog_debug(
849 "LSA[Type%d]: Graceful Restart in progress, don't originate",
850 OSPF_ROUTER_LSA);
851 return NULL;
852 }
853
d62a17ae 854 /* Create new router-LSA instance. */
855 if ((new = ospf_router_lsa_new(area)) == NULL) {
856 zlog_err("%s: ospf_router_lsa_new returned NULL", __func__);
857 return NULL;
858 }
859
860 /* Sanity check. */
975a328e 861 if (new->data->adv_router.s_addr == INADDR_ANY) {
d62a17ae 862 if (IS_DEBUG_OSPF_EVENT)
863 zlog_debug("LSA[Type1]: AdvRouter is 0, discard");
864 ospf_lsa_discard(new);
865 return NULL;
866 }
718e3744 867
d62a17ae 868 /* Install LSA to LSDB. */
869 new = ospf_lsa_install(area->ospf, NULL, new);
718e3744 870
d62a17ae 871 /* Update LSA origination count. */
872 area->ospf->lsa_originate_count++;
718e3744 873
d62a17ae 874 /* Flooding new LSA through area. */
875 ospf_flood_through_area(area, NULL, new);
718e3744 876
d62a17ae 877 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
878 zlog_debug("LSA[Type%d:%pI4]: Originate router-LSA %p",
879 new->data->type, &new->data->id,
d62a17ae 880 (void *)new);
881 ospf_lsa_header_dump(new->data);
882 }
718e3744 883
d62a17ae 884 return new;
718e3744 885}
886
887/* Refresh router-LSA. */
d62a17ae 888static struct ospf_lsa *ospf_router_lsa_refresh(struct ospf_lsa *lsa)
889{
890 struct ospf_area *area = lsa->area;
891 struct ospf_lsa *new;
892
893 /* Sanity check. */
894 assert(lsa->data);
718e3744 895
d62a17ae 896 /* Delete LSA from neighbor retransmit-list. */
897 ospf_ls_retransmit_delete_nbr_area(area, lsa);
718e3744 898
d62a17ae 899 /* Unregister LSA from refresh-list */
900 ospf_refresher_unregister_lsa(area->ospf, lsa);
718e3744 901
d62a17ae 902 /* Create new router-LSA instance. */
903 if ((new = ospf_router_lsa_new(area)) == NULL) {
904 zlog_err("%s: ospf_router_lsa_new returned NULL", __func__);
905 return NULL;
906 }
907
908 new->data->ls_seqnum = lsa_seqnum_increment(lsa);
718e3744 909
d62a17ae 910 ospf_lsa_install(area->ospf, NULL, new);
718e3744 911
d62a17ae 912 /* Flood LSA through area. */
913 ospf_flood_through_area(area, NULL, new);
914
915 /* Debug logging. */
916 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
917 zlog_debug("LSA[Type%d:%pI4]: router-LSA refresh",
918 new->data->type, &new->data->id);
d62a17ae 919 ospf_lsa_header_dump(new->data);
920 }
718e3744 921
d62a17ae 922 return NULL;
718e3744 923}
924
d62a17ae 925int ospf_router_lsa_update_area(struct ospf_area *area)
718e3744 926{
d62a17ae 927 if (IS_DEBUG_OSPF_EVENT)
928 zlog_debug("[router-LSA]: (router-LSA area update)");
718e3744 929
d62a17ae 930 /* Now refresh router-LSA. */
931 if (area->router_lsa_self)
932 ospf_lsa_refresh(area->ospf, area->router_lsa_self);
933 /* Newly originate router-LSA. */
934 else
935 ospf_router_lsa_originate(area);
718e3744 936
d62a17ae 937 return 0;
718e3744 938}
939
d62a17ae 940int ospf_router_lsa_update(struct ospf *ospf)
718e3744 941{
d62a17ae 942 struct listnode *node, *nnode;
943 struct ospf_area *area;
718e3744 944
d62a17ae 945 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
946 zlog_debug("Timer[router-LSA Update]: (timer expire)");
718e3744 947
d62a17ae 948 for (ALL_LIST_ELEMENTS(ospf->areas, node, nnode, area)) {
949 struct ospf_lsa *lsa = area->router_lsa_self;
950 struct router_lsa *rl;
951 const char *area_str;
718e3744 952
d62a17ae 953 /* Keep Area ID string. */
954 area_str = AREA_NAME(area);
718e3744 955
d62a17ae 956 /* If LSA not exist in this Area, originate new. */
957 if (lsa == NULL) {
958 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
959 zlog_debug(
960 "LSA[Type1]: Create router-LSA for Area %s",
961 area_str);
718e3744 962
d62a17ae 963 ospf_router_lsa_originate(area);
964 }
965 /* If router-ID is changed, Link ID must change.
966 First flush old LSA, then originate new. */
967 else if (!IPV4_ADDR_SAME(&lsa->data->id, &ospf->router_id)) {
968 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
969 zlog_debug(
96b663a3 970 "LSA[Type%d:%pI4]: Refresh router-LSA for Area %s",
d62a17ae 971 lsa->data->type,
96b663a3 972 &lsa->data->id, area_str);
d62a17ae 973 ospf_refresher_unregister_lsa(ospf, lsa);
974 ospf_lsa_flush_area(lsa, area);
975 ospf_lsa_unlock(&area->router_lsa_self);
976 area->router_lsa_self = NULL;
977
978 /* Refresh router-LSA, (not install) and flood through
979 * area. */
980 ospf_router_lsa_update_area(area);
981 } else {
982 rl = (struct router_lsa *)lsa->data;
983 /* Refresh router-LSA, (not install) and flood through
984 * area. */
985 if (rl->flags != ospf->flags)
986 ospf_router_lsa_update_area(area);
987 }
718e3744 988 }
718e3744 989
d62a17ae 990 return 0;
718e3744 991}
992
6b0655a2 993
718e3744 994/* network-LSA related functions. */
995/* Originate Network-LSA. */
d62a17ae 996static void ospf_network_lsa_body_set(struct stream *s,
997 struct ospf_interface *oi)
718e3744 998{
d62a17ae 999 struct in_addr mask;
1000 struct route_node *rn;
1001 struct ospf_neighbor *nbr;
718e3744 1002
d62a17ae 1003 masklen2ip(oi->address->prefixlen, &mask);
1004 stream_put_ipv4(s, mask.s_addr);
718e3744 1005
d62a17ae 1006 /* The network-LSA lists those routers that are fully adjacent to
1007 the Designated Router; each fully adjacent router is identified by
1008 its OSPF Router ID. The Designated Router includes itself in this
1009 list. RFC2328, Section 12.4.2 */
718e3744 1010
d62a17ae 1011 for (rn = route_top(oi->nbrs); rn; rn = route_next(rn))
1012 if ((nbr = rn->info) != NULL)
1013 if (nbr->state == NSM_Full || nbr == oi->nbr_self)
1014 stream_put_ipv4(s, nbr->router_id.s_addr);
718e3744 1015}
1016
d62a17ae 1017static struct ospf_lsa *ospf_network_lsa_new(struct ospf_interface *oi)
1018{
1019 struct stream *s;
1020 struct ospf_lsa *new;
1021 struct lsa_header *lsah;
1022 struct ospf_if_params *oip;
1023 int length;
1024
1025 /* If there are no neighbours on this network (the net is stub),
1026 the router does not originate network-LSA (see RFC 12.4.2) */
1027 if (oi->full_nbrs == 0)
1028 return NULL;
1029
1030 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1031 zlog_debug("LSA[Type2]: Create network-LSA instance");
1032
1033 /* Create new stream for LSA. */
1034 s = stream_new(OSPF_MAX_LSA_SIZE);
1035 lsah = (struct lsa_header *)STREAM_DATA(s);
1036
1037 lsa_header_set(s, (OPTIONS(oi) | LSA_OPTIONS_GET(oi->area)),
1038 OSPF_NETWORK_LSA, DR(oi), oi->ospf->router_id);
1039
1040 /* Set network-LSA body fields. */
1041 ospf_network_lsa_body_set(s, oi);
1042
1043 /* Set length. */
1044 length = stream_get_endp(s);
1045 lsah->length = htons(length);
1046
1047 /* Create OSPF LSA instance. */
5b3d4186 1048 new = ospf_lsa_new_and_data(length);
d62a17ae 1049
1050 new->area = oi->area;
1051 SET_FLAG(new->flags, OSPF_LSA_SELF | OSPF_LSA_SELF_CHECKED);
b5a8894d 1052 new->vrf_id = oi->ospf->vrf_id;
d62a17ae 1053
1054 /* Copy LSA to store. */
d62a17ae 1055 memcpy(new->data, lsah, length);
1056 stream_free(s);
1057
1058 /* Remember prior network LSA sequence numbers, even if we stop
1059 * originating one for this oi, to try avoid re-originating LSAs with a
1060 * prior sequence number, and thus speed up adjency forming &
1061 * convergence.
1062 */
1063 if ((oip = ospf_lookup_if_params(oi->ifp, oi->address->u.prefix4))) {
1064 new->data->ls_seqnum = oip->network_lsa_seqnum;
1065 new->data->ls_seqnum = lsa_seqnum_increment(new);
1066 } else {
1067 oip = ospf_get_if_params(oi->ifp, oi->address->u.prefix4);
1068 ospf_if_update_params(oi->ifp, oi->address->u.prefix4);
1069 }
1070 oip->network_lsa_seqnum = new->data->ls_seqnum;
1071
1072 return new;
718e3744 1073}
1074
1075/* Originate network-LSA. */
d62a17ae 1076void ospf_network_lsa_update(struct ospf_interface *oi)
718e3744 1077{
d62a17ae 1078 struct ospf_lsa *new;
718e3744 1079
10514170
RW
1080 if (oi->area->ospf->gr_info.restart_in_progress) {
1081 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1082 zlog_debug(
1083 "LSA[Type%d]: Graceful Restart in progress, don't originate",
1084 OSPF_NETWORK_LSA);
1085 return;
1086 }
1087
d62a17ae 1088 if (oi->network_lsa_self != NULL) {
1089 ospf_lsa_refresh(oi->ospf, oi->network_lsa_self);
1090 return;
1091 }
1092
1093 /* Create new network-LSA instance. */
1094 new = ospf_network_lsa_new(oi);
1095 if (new == NULL)
1096 return;
718e3744 1097
d62a17ae 1098 /* Install LSA to LSDB. */
1099 new = ospf_lsa_install(oi->ospf, oi, new);
718e3744 1100
d62a17ae 1101 /* Update LSA origination count. */
1102 oi->ospf->lsa_originate_count++;
718e3744 1103
d62a17ae 1104 /* Flooding new LSA through area. */
1105 ospf_flood_through_area(oi->area, NULL, new);
1106
1107 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
1108 zlog_debug("LSA[Type%d:%pI4]: Originate network-LSA %p",
1109 new->data->type, &new->data->id,
d62a17ae 1110 (void *)new);
1111 ospf_lsa_header_dump(new->data);
1112 }
718e3744 1113
d62a17ae 1114 return;
718e3744 1115}
1116
d62a17ae 1117static struct ospf_lsa *ospf_network_lsa_refresh(struct ospf_lsa *lsa)
1118{
1119 struct ospf_area *area = lsa->area;
1120 struct ospf_lsa *new, *new2;
1121 struct ospf_if_params *oip;
1122 struct ospf_interface *oi;
1123
1124 assert(lsa->data);
1125
1126 /* Retrieve the oi for the network LSA */
1127 oi = ospf_if_lookup_by_local_addr(area->ospf, NULL, lsa->data->id);
1128 if (oi == NULL) {
1129 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
1130 zlog_debug(
96b663a3
MS
1131 "LSA[Type%d:%pI4]: network-LSA refresh: no oi found, ick, ignoring.",
1132 lsa->data->type, &lsa->data->id);
d62a17ae 1133 ospf_lsa_header_dump(lsa->data);
1134 }
1135 return NULL;
1136 }
1137 /* Delete LSA from neighbor retransmit-list. */
1138 ospf_ls_retransmit_delete_nbr_area(area, lsa);
1139
1140 /* Unregister LSA from refresh-list */
1141 ospf_refresher_unregister_lsa(area->ospf, lsa);
1142
1143 /* Create new network-LSA instance. */
1144 new = ospf_network_lsa_new(oi);
1145 if (new == NULL)
1146 return NULL;
1147
1148 oip = ospf_lookup_if_params(oi->ifp, oi->address->u.prefix4);
1149 assert(oip != NULL);
1150 oip->network_lsa_seqnum = new->data->ls_seqnum =
1151 lsa_seqnum_increment(lsa);
1152
1153 new2 = ospf_lsa_install(area->ospf, oi, new);
1154
1155 assert(new2 == new);
1156
1157 /* Flood LSA through aera. */
1158 ospf_flood_through_area(area, NULL, new);
1159
1160 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
1161 zlog_debug("LSA[Type%d:%pI4]: network-LSA refresh",
1162 new->data->type, &new->data->id);
d62a17ae 1163 ospf_lsa_header_dump(new->data);
1164 }
1165
1166 return new;
1167}
1168
d7c0a89a 1169static void stream_put_ospf_metric(struct stream *s, uint32_t metric_value)
d62a17ae 1170{
d7c0a89a 1171 uint32_t metric;
d62a17ae 1172 char *mp;
1173
1174 /* Put 0 metric. TOS metric is not supported. */
1175 metric = htonl(metric_value);
1176 mp = (char *)&metric;
1177 mp++;
1178 stream_put(s, mp, 3);
718e3744 1179}
1180
1181/* summary-LSA related functions. */
d62a17ae 1182static void ospf_summary_lsa_body_set(struct stream *s, struct prefix *p,
d7c0a89a 1183 uint32_t metric)
718e3744 1184{
d62a17ae 1185 struct in_addr mask;
718e3744 1186
d62a17ae 1187 masklen2ip(p->prefixlen, &mask);
718e3744 1188
d62a17ae 1189 /* Put Network Mask. */
1190 stream_put_ipv4(s, mask.s_addr);
718e3744 1191
d62a17ae 1192 /* Set # TOS. */
d7c0a89a 1193 stream_putc(s, (uint8_t)0);
718e3744 1194
d62a17ae 1195 /* Set metric. */
1196 stream_put_ospf_metric(s, metric);
718e3744 1197}
1198
d62a17ae 1199static struct ospf_lsa *ospf_summary_lsa_new(struct ospf_area *area,
d7c0a89a 1200 struct prefix *p, uint32_t metric,
d62a17ae 1201 struct in_addr id)
718e3744 1202{
d62a17ae 1203 struct stream *s;
1204 struct ospf_lsa *new;
1205 struct lsa_header *lsah;
1206 int length;
718e3744 1207
d62a17ae 1208 if (id.s_addr == 0xffffffff) {
1209 /* Maybe Link State ID not available. */
1210 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1211 zlog_debug(
1212 "LSA[Type%d]: Link ID not available, can't originate",
1213 OSPF_SUMMARY_LSA);
1214 return NULL;
1215 }
c24d602e 1216
d62a17ae 1217 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1218 zlog_debug("LSA[Type3]: Create summary-LSA instance");
718e3744 1219
d62a17ae 1220 /* Create new stream for LSA. */
1221 s = stream_new(OSPF_MAX_LSA_SIZE);
1222 lsah = (struct lsa_header *)STREAM_DATA(s);
718e3744 1223
d62a17ae 1224 lsa_header_set(s, LSA_OPTIONS_GET(area), OSPF_SUMMARY_LSA, id,
1225 area->ospf->router_id);
718e3744 1226
d62a17ae 1227 /* Set summary-LSA body fields. */
1228 ospf_summary_lsa_body_set(s, p, metric);
718e3744 1229
d62a17ae 1230 /* Set length. */
1231 length = stream_get_endp(s);
1232 lsah->length = htons(length);
718e3744 1233
d62a17ae 1234 /* Create OSPF LSA instance. */
5b3d4186 1235 new = ospf_lsa_new_and_data(length);
d62a17ae 1236 new->area = area;
1237 SET_FLAG(new->flags, OSPF_LSA_SELF | OSPF_LSA_SELF_CHECKED);
b5a8894d 1238 new->vrf_id = area->ospf->vrf_id;
718e3744 1239
d62a17ae 1240 /* Copy LSA to store. */
d62a17ae 1241 memcpy(new->data, lsah, length);
1242 stream_free(s);
718e3744 1243
d62a17ae 1244 return new;
718e3744 1245}
1246
1247/* Originate Summary-LSA. */
a8c22275 1248static struct ospf_lsa *
1249ospf_summary_lsa_prepare_and_flood(struct prefix_ipv4 *p, uint32_t metric,
1250 struct ospf_area *area, struct in_addr id)
d62a17ae 1251{
1252 struct ospf_lsa *new;
d62a17ae 1253
1254 /* Create new summary-LSA instance. */
1255 if (!(new = ospf_summary_lsa_new(area, (struct prefix *)p, metric, id)))
1256 return NULL;
1257
1258 /* Instlal LSA to LSDB. */
1259 new = ospf_lsa_install(area->ospf, NULL, new);
1260
1261 /* Update LSA origination count. */
1262 area->ospf->lsa_originate_count++;
1263
1264 /* Flooding new LSA through area. */
1265 ospf_flood_through_area(area, NULL, new);
1266
1267 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
1268 zlog_debug("LSA[Type%d:%pI4]: Originate summary-LSA %p",
1269 new->data->type, &new->data->id,
d62a17ae 1270 (void *)new);
1271 ospf_lsa_header_dump(new->data);
1272 }
1273
1274 return new;
1275}
1276
a8c22275 1277static struct ospf_lsa *ospf_handle_summarylsa_lsId_chg(struct ospf *ospf,
1278 struct prefix_ipv4 *p,
1279 uint8_t type,
1280 uint32_t metric,
1281 struct in_addr old_id)
1282{
1283 struct ospf_lsa *lsa = NULL;
1284 struct ospf_lsa *new = NULL;
1285 struct summary_lsa *sl = NULL;
1286 struct ospf_area *old_area = NULL;
1287 struct prefix_ipv4 old_prefix;
1288 uint32_t old_metric;
1289 struct in_addr mask;
1290 uint32_t metric_val;
1291 char *metric_buf;
1292
1293 lsa = ospf_lsdb_lookup_by_id(ospf->lsdb, type, p->prefix,
1294 ospf->router_id);
1295
1296 if (!lsa) {
1297 flog_warn(EC_OSPF_LSA_NULL, "(%s): LSA not found", __func__);
1298 return NULL;
1299 }
1300
1301 sl = (struct summary_lsa *)lsa->data;
1302
1303 old_area = lsa->area;
1304 old_metric = GET_METRIC(sl->metric);
1305 old_prefix.prefix = sl->header.id;
1306 old_prefix.prefixlen = ip_masklen(sl->mask);
1307 old_prefix.family = AF_INET;
1308
1309
1310 /* change the mask */
1311 masklen2ip(p->prefixlen, &mask);
1312 sl->mask.s_addr = mask.s_addr;
1313
1314 /* Copy the metric*/
1315 metric_val = htonl(metric);
1316 metric_buf = (char *)&metric_val;
1317 memcpy(sl->metric, metric_buf, sizeof(metric_val));
1318
1319 if (type == OSPF_SUMMARY_LSA) {
1320 /*Refresh the LSA with new LSA*/
1321 ospf_summary_lsa_refresh(ospf, lsa);
1322
1323 new = ospf_summary_lsa_prepare_and_flood(
1324 &old_prefix, old_metric, old_area, old_id);
1325 } else {
1326 /*Refresh the LSA with new LSA*/
1327 ospf_summary_asbr_lsa_refresh(ospf, lsa);
1328
1329 new = ospf_asbr_summary_lsa_prepare_and_flood(
1330 &old_prefix, old_metric, old_area, old_id);
1331 }
1332
1333 return new;
1334}
1335
1336/* Originate Summary-LSA. */
1337struct ospf_lsa *ospf_summary_lsa_originate(struct prefix_ipv4 *p,
1338 uint32_t metric,
1339 struct ospf_area *area)
1340{
1341 struct in_addr id;
1342 enum lsid_status status;
1343 struct ospf_lsa *new = NULL;
1344
1345 status = ospf_lsa_unique_id(area->ospf, area->lsdb, OSPF_SUMMARY_LSA, p,
1346 &id);
1347
1348 if (status == LSID_CHANGE) {
1349 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1350 zlog_debug("Link ID has to be changed.");
1351
1352 new = ospf_handle_summarylsa_lsId_chg(
1353 area->ospf, p, OSPF_SUMMARY_LSA, metric, id);
1354 return new;
1355 } else if (status == LSID_NOT_AVAILABLE) {
1356 /* Link State ID not available. */
1357 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1358 zlog_debug(
1359 "LSA[Type5]: Link ID not available, can't originate");
1360
1361 return NULL;
1362 }
1363
1364 new = ospf_summary_lsa_prepare_and_flood(p, metric, area, id);
1365 return new;
1366}
1367
d62a17ae 1368static struct ospf_lsa *ospf_summary_lsa_refresh(struct ospf *ospf,
1369 struct ospf_lsa *lsa)
1370{
1371 struct ospf_lsa *new;
1372 struct summary_lsa *sl;
1373 struct prefix p;
1374
1375 /* Sanity check. */
1376 assert(lsa->data);
1377
1378 sl = (struct summary_lsa *)lsa->data;
1379 p.prefixlen = ip_masklen(sl->mask);
1380 new = ospf_summary_lsa_new(lsa->area, &p, GET_METRIC(sl->metric),
1381 sl->header.id);
1382
1383 if (!new)
1384 return NULL;
1385
1386 new->data->ls_seqnum = lsa_seqnum_increment(lsa);
1387
1388 ospf_lsa_install(ospf, NULL, new);
1389
1390 /* Flood LSA through AS. */
1391 ospf_flood_through_area(new->area, NULL, new);
1392
1393 /* Debug logging. */
1394 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
1395 zlog_debug("LSA[Type%d:%pI4]: summary-LSA refresh",
1396 new->data->type, &new->data->id);
d62a17ae 1397 ospf_lsa_header_dump(new->data);
1398 }
1399
1400 return new;
718e3744 1401}
1402
6b0655a2 1403
718e3744 1404/* summary-ASBR-LSA related functions. */
d62a17ae 1405static void ospf_summary_asbr_lsa_body_set(struct stream *s, struct prefix *p,
d7c0a89a 1406 uint32_t metric)
718e3744 1407{
d62a17ae 1408 /* Put Network Mask. */
d7c0a89a 1409 stream_put_ipv4(s, (uint32_t)0);
718e3744 1410
d62a17ae 1411 /* Set # TOS. */
d7c0a89a 1412 stream_putc(s, (uint8_t)0);
718e3744 1413
d62a17ae 1414 /* Set metric. */
1415 stream_put_ospf_metric(s, metric);
718e3744 1416}
1417
d62a17ae 1418static struct ospf_lsa *ospf_summary_asbr_lsa_new(struct ospf_area *area,
1419 struct prefix *p,
d7c0a89a 1420 uint32_t metric,
d62a17ae 1421 struct in_addr id)
718e3744 1422{
d62a17ae 1423 struct stream *s;
1424 struct ospf_lsa *new;
1425 struct lsa_header *lsah;
1426 int length;
718e3744 1427
d62a17ae 1428 if (id.s_addr == 0xffffffff) {
1429 /* Maybe Link State ID not available. */
1430 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1431 zlog_debug(
1432 "LSA[Type%d]: Link ID not available, can't originate",
1433 OSPF_ASBR_SUMMARY_LSA);
1434 return NULL;
1435 }
c24d602e 1436
d62a17ae 1437 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1438 zlog_debug("LSA[Type3]: Create summary-LSA instance");
718e3744 1439
d62a17ae 1440 /* Create new stream for LSA. */
1441 s = stream_new(OSPF_MAX_LSA_SIZE);
1442 lsah = (struct lsa_header *)STREAM_DATA(s);
718e3744 1443
d62a17ae 1444 lsa_header_set(s, LSA_OPTIONS_GET(area), OSPF_ASBR_SUMMARY_LSA, id,
1445 area->ospf->router_id);
718e3744 1446
d62a17ae 1447 /* Set summary-LSA body fields. */
1448 ospf_summary_asbr_lsa_body_set(s, p, metric);
718e3744 1449
d62a17ae 1450 /* Set length. */
1451 length = stream_get_endp(s);
1452 lsah->length = htons(length);
718e3744 1453
d62a17ae 1454 /* Create OSPF LSA instance. */
5b3d4186 1455 new = ospf_lsa_new_and_data(length);
d62a17ae 1456 new->area = area;
1457 SET_FLAG(new->flags, OSPF_LSA_SELF | OSPF_LSA_SELF_CHECKED);
b5a8894d 1458 new->vrf_id = area->ospf->vrf_id;
718e3744 1459
d62a17ae 1460 /* Copy LSA to store. */
d62a17ae 1461 memcpy(new->data, lsah, length);
1462 stream_free(s);
718e3744 1463
d62a17ae 1464 return new;
718e3744 1465}
1466
1467/* Originate summary-ASBR-LSA. */
a8c22275 1468static struct ospf_lsa *
1469ospf_asbr_summary_lsa_prepare_and_flood(struct prefix_ipv4 *p, uint32_t metric,
1470 struct ospf_area *area,
1471 struct in_addr id)
d62a17ae 1472{
1473 struct ospf_lsa *new;
d62a17ae 1474
1475 /* Create new summary-LSA instance. */
1476 new = ospf_summary_asbr_lsa_new(area, (struct prefix *)p, metric, id);
1477 if (!new)
1478 return NULL;
1479
1480 /* Install LSA to LSDB. */
1481 new = ospf_lsa_install(area->ospf, NULL, new);
718e3744 1482
d62a17ae 1483 /* Update LSA origination count. */
1484 area->ospf->lsa_originate_count++;
718e3744 1485
d62a17ae 1486 /* Flooding new LSA through area. */
1487 ospf_flood_through_area(area, NULL, new);
718e3744 1488
d62a17ae 1489 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
1490 zlog_debug("LSA[Type%d:%pI4]: Originate summary-ASBR-LSA %p",
1491 new->data->type, &new->data->id,
d62a17ae 1492 (void *)new);
1493 ospf_lsa_header_dump(new->data);
1494 }
1495
1496 return new;
1497}
1498
a8c22275 1499struct ospf_lsa *ospf_summary_asbr_lsa_originate(struct prefix_ipv4 *p,
1500 uint32_t metric,
1501 struct ospf_area *area)
1502{
1503 struct ospf_lsa *new;
1504 struct in_addr id;
1505 enum lsid_status status;
1506
1507 status = ospf_lsa_unique_id(area->ospf, area->lsdb,
1508 OSPF_ASBR_SUMMARY_LSA, p, &id);
1509
1510 if (status == LSID_CHANGE) {
1511 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1512 zlog_debug("Link ID has to be changed.");
1513
1514 new = ospf_handle_summarylsa_lsId_chg(
1515 area->ospf, p, OSPF_ASBR_SUMMARY_LSA, metric, id);
1516 return new;
1517 } else if (status == LSID_NOT_AVAILABLE) {
1518 /* Link State ID not available. */
1519 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1520 zlog_debug(
1521 "LSA[Type5]: Link ID not available, can't originate");
1522
1523 return NULL;
1524 }
1525
1526 new = ospf_asbr_summary_lsa_prepare_and_flood(p, metric, area, id);
1527 return new;
1528}
1529
d62a17ae 1530static struct ospf_lsa *ospf_summary_asbr_lsa_refresh(struct ospf *ospf,
1531 struct ospf_lsa *lsa)
1532{
1533 struct ospf_lsa *new;
1534 struct summary_lsa *sl;
1535 struct prefix p;
1536
1537 /* Sanity check. */
1538 assert(lsa->data);
1539
1540 sl = (struct summary_lsa *)lsa->data;
1541 p.prefixlen = ip_masklen(sl->mask);
1542 new = ospf_summary_asbr_lsa_new(lsa->area, &p, GET_METRIC(sl->metric),
1543 sl->header.id);
1544 if (!new)
1545 return NULL;
1546
1547 new->data->ls_seqnum = lsa_seqnum_increment(lsa);
1548
1549 ospf_lsa_install(ospf, NULL, new);
1550
1551 /* Flood LSA through area. */
1552 ospf_flood_through_area(new->area, NULL, new);
1553
1554 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
1555 zlog_debug("LSA[Type%d:%pI4]: summary-ASBR-LSA refresh",
1556 new->data->type, &new->data->id);
d62a17ae 1557 ospf_lsa_header_dump(new->data);
1558 }
1559
1560 return new;
718e3744 1561}
1562
1563/* AS-external-LSA related functions. */
1564
1565/* Get nexthop for AS-external-LSAs. Return nexthop if its interface
1566 is connected, else 0*/
d62a17ae 1567static struct in_addr ospf_external_lsa_nexthop_get(struct ospf *ospf,
1568 struct in_addr nexthop)
718e3744 1569{
d62a17ae 1570 struct in_addr fwd;
1571 struct prefix nh;
1572 struct listnode *node;
1573 struct ospf_interface *oi;
1574
1575 fwd.s_addr = 0;
718e3744 1576
d62a17ae 1577 if (!nexthop.s_addr)
1578 return fwd;
718e3744 1579
d62a17ae 1580 /* Check whether nexthop is covered by OSPF network. */
1581 nh.family = AF_INET;
1582 nh.u.prefix4 = nexthop;
1583 nh.prefixlen = IPV4_MAX_BITLEN;
718e3744 1584
d62a17ae 1585 /* XXX/SCALE: If there were a lot of oi's on an ifp, then it'd be
1586 * better to make use of the per-ifp table of ois.
1587 */
1588 for (ALL_LIST_ELEMENTS_RO(ospf->oiflist, node, oi))
1589 if (if_is_operative(oi->ifp))
1590 if (oi->address->family == AF_INET)
1591 if (prefix_match(oi->address, &nh))
1592 return nexthop;
718e3744 1593
d62a17ae 1594 return fwd;
718e3744 1595}
1596
718e3744 1597/* NSSA-external-LSA related functions. */
1598
1599/* Get 1st IP connection for Forward Addr */
4dadc291 1600
d62a17ae 1601struct in_addr ospf_get_ip_from_ifp(struct ospf_interface *oi)
718e3744 1602{
d62a17ae 1603 struct in_addr fwd;
718e3744 1604
975a328e 1605 fwd.s_addr = INADDR_ANY;
718e3744 1606
d62a17ae 1607 if (if_is_operative(oi->ifp))
1608 return oi->address->u.prefix4;
1609
1610 return fwd;
718e3744 1611}
1612
1613/* Get 1st IP connection for Forward Addr */
d62a17ae 1614struct in_addr ospf_get_nssa_ip(struct ospf_area *area)
1615{
1616 struct in_addr fwd;
1617 struct in_addr best_default;
1618 struct listnode *node;
1619 struct ospf_interface *oi;
1620
1621 fwd.s_addr = 0;
1622 best_default.s_addr = 0;
1623
1624 for (ALL_LIST_ELEMENTS_RO(area->ospf->oiflist, node, oi)) {
1625 if (if_is_operative(oi->ifp))
1626 if (oi->area->external_routing == OSPF_AREA_NSSA)
1627 if (oi->address
1628 && oi->address->family == AF_INET) {
3a6290bd 1629 if (best_default.s_addr == INADDR_ANY)
d62a17ae 1630 best_default =
1631 oi->address->u.prefix4;
1632 if (oi->area == area)
1633 return oi->address->u.prefix4;
1634 }
1635 }
3a6290bd 1636 if (best_default.s_addr != INADDR_ANY)
d62a17ae 1637 return best_default;
718e3744 1638
3a6290bd 1639 if (best_default.s_addr != INADDR_ANY)
d62a17ae 1640 return best_default;
68980084 1641
d62a17ae 1642 return fwd;
718e3744 1643}
beebba75 1644
d7c0a89a 1645int metric_type(struct ospf *ospf, uint8_t src, unsigned short instance)
718e3744 1646{
d62a17ae 1647 struct ospf_redist *red;
7c8ff89e 1648
d62a17ae 1649 red = ospf_redist_lookup(ospf, src, instance);
7c8ff89e 1650
d62a17ae 1651 return ((!red || red->dmetric.type < 0) ? DEFAULT_METRIC_TYPE
1652 : red->dmetric.type);
718e3744 1653}
1654
d7c0a89a 1655int metric_value(struct ospf *ospf, uint8_t src, unsigned short instance)
718e3744 1656{
d62a17ae 1657 struct ospf_redist *red;
7c8ff89e 1658
d62a17ae 1659 red = ospf_redist_lookup(ospf, src, instance);
1660 if (!red || red->dmetric.value < 0) {
1661 if (src == DEFAULT_ROUTE) {
1662 if (ospf->default_originate == DEFAULT_ORIGINATE_ZEBRA)
1663 return DEFAULT_DEFAULT_ORIGINATE_METRIC;
1664 else
1665 return DEFAULT_DEFAULT_ALWAYS_METRIC;
1666 } else if (ospf->default_metric < 0)
1667 return DEFAULT_DEFAULT_METRIC;
1668 else
1669 return ospf->default_metric;
718e3744 1670 }
718e3744 1671
d62a17ae 1672 return red->dmetric.value;
718e3744 1673}
1674
1675/* Set AS-external-LSA body. */
d62a17ae 1676static void ospf_external_lsa_body_set(struct stream *s,
1677 struct external_info *ei,
1678 struct ospf *ospf)
1679{
1680 struct prefix_ipv4 *p = &ei->p;
1681 struct in_addr mask, fwd_addr;
d7c0a89a 1682 uint32_t mvalue;
d62a17ae 1683 int mtype;
1684 int type;
d7c0a89a 1685 unsigned short instance;
d62a17ae 1686
1687 /* Put Network Mask. */
1688 masklen2ip(p->prefixlen, &mask);
1689 stream_put_ipv4(s, mask.s_addr);
1690
1691 /* If prefix is default, specify DEFAULT_ROUTE. */
1fe59b44
RZ
1692 type = is_default_prefix4(&ei->p) ? DEFAULT_ROUTE : ei->type;
1693 instance = is_default_prefix4(&ei->p) ? 0 : ei->instance;
d62a17ae 1694
1695 mtype = (ROUTEMAP_METRIC_TYPE(ei) != -1)
1696 ? ROUTEMAP_METRIC_TYPE(ei)
1697 : metric_type(ospf, type, instance);
1698
1699 mvalue = (ROUTEMAP_METRIC(ei) != -1)
1700 ? ROUTEMAP_METRIC(ei)
1701 : metric_value(ospf, type, instance);
1702
1703 /* Put type of external metric. */
1704 stream_putc(s, (mtype == EXTERNAL_METRIC_TYPE_2 ? 0x80 : 0));
1705
1706 /* Put 0 metric. TOS metric is not supported. */
1707 stream_put_ospf_metric(s, mvalue);
1708
1709 /* Get forwarding address to nexthop if on the Connection List, else 0.
1710 */
1711 fwd_addr = ospf_external_lsa_nexthop_get(ospf, ei->nexthop);
1712
1713 /* Put forwarding address. */
1714 stream_put_ipv4(s, fwd_addr.s_addr);
1715
1716 /* Put route tag */
1717 stream_putl(s, ei->tag);
718e3744 1718}
1719
1720/* Create new external-LSA. */
a8c22275 1721static struct ospf_lsa *
1722ospf_exnl_lsa_prepare_and_flood(struct ospf *ospf, struct external_info *ei,
1723 struct in_addr id)
d62a17ae 1724{
1725 struct stream *s;
1726 struct lsa_header *lsah;
1727 struct ospf_lsa *new;
d62a17ae 1728 int length;
1729
d62a17ae 1730 /* Create new stream for LSA. */
1731 s = stream_new(OSPF_MAX_LSA_SIZE);
1732 lsah = (struct lsa_header *)STREAM_DATA(s);
1733
1734 /* Set LSA common header fields. */
1735 lsa_header_set(s, OSPF_OPTION_E, OSPF_AS_EXTERNAL_LSA, id,
1736 ospf->router_id);
1737
1738 /* Set AS-external-LSA body fields. */
1739 ospf_external_lsa_body_set(s, ei, ospf);
1740
1741 /* Set length. */
1742 length = stream_get_endp(s);
1743 lsah->length = htons(length);
1744
1745 /* Now, create OSPF LSA instance. */
5b3d4186 1746 new = ospf_lsa_new_and_data(length);
d62a17ae 1747 new->area = NULL;
1748 SET_FLAG(new->flags,
1749 OSPF_LSA_SELF | OSPF_LSA_APPROVED | OSPF_LSA_SELF_CHECKED);
b5a8894d 1750 new->vrf_id = ospf->vrf_id;
d62a17ae 1751
1752 /* Copy LSA data to store, discard stream. */
d62a17ae 1753 memcpy(new->data, lsah, length);
1754 stream_free(s);
1755
1756 return new;
718e3744 1757}
1758
a8c22275 1759static struct ospf_lsa *ospf_handle_exnl_lsa_lsId_chg(struct ospf *ospf,
1760 struct external_info *ei,
1761 struct in_addr id)
1762{
1763 struct ospf_lsa *lsa;
1764 struct as_external_lsa *al;
1765 struct in_addr mask;
1766 struct ospf_lsa *new;
c33e80d5 1767 struct external_info ei_summary = {};
a8c22275 1768 struct external_info *ei_old;
1769
1770 lsa = ospf_lsdb_lookup_by_id(ospf->lsdb, OSPF_AS_EXTERNAL_LSA,
1771 ei->p.prefix, ospf->router_id);
1772
1773 if (!lsa) {
1774 flog_warn(EC_OSPF_LSA_NULL, "(%s): LSA not found", __func__);
1775 return NULL;
1776 }
1777
1778 ei_old = ospf_external_info_check(ospf, lsa);
1779
1780 al = (struct as_external_lsa *)lsa->data;
1781
1782 if (!ei_old) {
1783 /* eii_old pointer of LSA is NULL, this
1784 * must be external aggregate route.
1785 */
1786 ei_summary.p.family = AF_INET;
1787 ei_summary.p.prefix = al->header.id;
1788 ei_summary.p.prefixlen = ip_masklen(al->mask);
1789 ei_summary.tag = (unsigned long)ntohl(al->e[0].route_tag);
1790 ei_old = &ei_summary;
1791 }
1792
1793 /* change the mask */
1794 masklen2ip(ei->p.prefixlen, &mask);
1795 al->mask.s_addr = mask.s_addr;
1796
1797 /*Refresh the LSA with new LSA*/
1798 ospf_external_lsa_refresh(ospf, lsa, ei, LSA_REFRESH_FORCE, 0);
1799
1800 /*Originate the old LSA with changed LSID*/
1801 new = ospf_exnl_lsa_prepare_and_flood(ospf, ei_old, id);
1802
1803 return new;
1804}
1805
1806static struct ospf_lsa *ospf_external_lsa_new(struct ospf *ospf,
1807 struct external_info *ei,
1808 struct in_addr *old_id)
1809{
1810 struct ospf_lsa *new;
1811 struct in_addr id;
1812 enum lsid_status status;
1813
1814 if (ei == NULL) {
1815 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1816 zlog_debug(
1817 "LSA[Type5]: External info is NULL, can't originate");
1818 return NULL;
1819 }
1820
1821 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1822 zlog_debug("LSA[Type5]: Originate AS-external-LSA instance");
1823
1824 /* If old Link State ID is specified, refresh LSA with same ID. */
1825 if (old_id)
1826 id = *old_id;
1827 /* Get Link State with unique ID. */
1828 else {
1829 status = ospf_lsa_unique_id(ospf, ospf->lsdb,
1830 OSPF_AS_EXTERNAL_LSA, &ei->p, &id);
1831
1832 if (status == LSID_CHANGE) {
1833 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1834 zlog_debug("Link ID has to be changed.");
1835
1836 new = ospf_handle_exnl_lsa_lsId_chg(ospf, ei, id);
1837 return new;
1838 } else if (status == LSID_NOT_AVAILABLE) {
1839 /* Link State ID not available. */
1840 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
1841 zlog_debug(
1842 "LSA[Type5]: Link ID not available, can't originate");
1843 return NULL;
1844 }
1845 }
1846
1847 new = ospf_exnl_lsa_prepare_and_flood(ospf, ei, id);
1848
1849 return new;
1850}
1851
718e3744 1852/* As Type-7 */
d62a17ae 1853static void ospf_install_flood_nssa(struct ospf *ospf, struct ospf_lsa *lsa,
1854 struct external_info *ei)
1855{
1856 struct ospf_lsa *new;
1857 struct as_external_lsa *extlsa;
1858 struct ospf_area *area;
1859 struct listnode *node, *nnode;
1860
1861 /* LSA may be a Type-5 originated via translation of a Type-7 LSA
1862 * which originated from an NSSA area. In which case it should not be
1863 * flooded back to NSSA areas.
1864 */
1865 if (CHECK_FLAG(lsa->flags, OSPF_LSA_LOCAL_XLT))
1866 return;
1867
1868 /* NSSA Originate or Refresh (If anyNSSA)
1869
1870 LSA is self-originated. And just installed as Type-5.
1871 Additionally, install as Type-7 LSDB for every attached NSSA.
1872
1873 P-Bit controls which ABR performs translation to outside world; If
1874 we are an ABR....do not set the P-bit, because we send the Type-5,
1875 not as the ABR Translator, but as the ASBR owner within the AS!
1876
1877 If we are NOT ABR, Flood through NSSA as Type-7 w/P-bit set. The
1878 elected ABR Translator will see the P-bit, Translate, and re-flood.
1879
1880 Later, ABR_TASK and P-bit will scan Type-7 LSDB and translate to
1881 Type-5's to non-NSSA Areas. (it will also attempt a re-install) */
1882
1883 for (ALL_LIST_ELEMENTS(ospf->areas, node, nnode, area)) {
1884 /* Don't install Type-7 LSA's into nonNSSA area */
1885 if (area->external_routing != OSPF_AREA_NSSA)
1886 continue;
1887
1888 /* make lsa duplicate, lock=1 */
1889 new = ospf_lsa_dup(lsa);
1890 new->area = area;
1891 new->data->type = OSPF_AS_NSSA_LSA;
1892
1893 /* set P-bit if not ABR */
1894 if (!IS_OSPF_ABR(ospf)) {
1895 SET_FLAG(new->data->options, OSPF_OPTION_NP);
1896
1897 /* set non-zero FWD ADDR
1898
1899 draft-ietf-ospf-nssa-update-09.txt
1900
1901 if the network between the NSSA AS boundary router and
1902 the
1903 adjacent AS is advertised into OSPF as an internal OSPF
1904 route,
1905 the forwarding address should be the next op address as
1906 is cu
1907 currently done with type-5 LSAs. If the intervening
1908 network is
1909 not adversited into OSPF as an internal OSPF route and
1910 the
1911 type-7 LSA's P-bit is set a forwarding address should be
87bd50e8 1912 selected from one of the router's active OSPF interface
d62a17ae 1913 addresses
1914 which belong to the NSSA. If no such addresses exist,
1915 then
1916 no type-7 LSA's with the P-bit set should originate from
1917 this
1918 router. */
1919
1920 /* kevinm: not updating lsa anymore, just new */
1921 extlsa = (struct as_external_lsa *)(new->data);
1922
3a6290bd 1923 if (extlsa->e[0].fwd_addr.s_addr == INADDR_ANY)
d62a17ae 1924 extlsa->e[0].fwd_addr = ospf_get_nssa_ip(
1925 area); /* this NSSA area in ifp */
1926
3a6290bd 1927 if (extlsa->e[0].fwd_addr.s_addr == INADDR_ANY) {
d62a17ae 1928 if (IS_DEBUG_OSPF_NSSA)
1929 zlog_debug(
1930 "LSA[Type-7]: Could not build FWD-ADDR");
1931 ospf_lsa_discard(new);
1932 return;
1933 }
1934 }
1935
1936 /* install also as Type-7 */
1937 ospf_lsa_install(ospf, NULL,
1938 new); /* Remove Old, Lock New = 2 */
1939
1940 /* will send each copy, lock=2+n */
1941 ospf_flood_through_as(
1942 ospf, NULL, new); /* all attached NSSA's, no AS/STUBs */
1943 }
d4a53d58 1944}
1945
d62a17ae 1946static struct ospf_lsa *ospf_lsa_translated_nssa_new(struct ospf *ospf,
1947 struct ospf_lsa *type7)
1948{
1949
1950 struct ospf_lsa *new;
1951 struct as_external_lsa *ext, *extnew;
1952 struct external_info ei;
1953
1954 ext = (struct as_external_lsa *)(type7->data);
1955
1956 /* need external_info struct, fill in bare minimum */
1957 ei.p.family = AF_INET;
1958 ei.p.prefix = type7->data->id;
1959 ei.p.prefixlen = ip_masklen(ext->mask);
1960 ei.type = ZEBRA_ROUTE_OSPF;
1961 ei.nexthop = ext->header.adv_router;
1962 ei.route_map_set.metric = -1;
1963 ei.route_map_set.metric_type = -1;
1964 ei.tag = 0;
12a81f8e 1965 ei.instance = 0;
d62a17ae 1966
1967 if ((new = ospf_external_lsa_new(ospf, &ei, &type7->data->id))
1968 == NULL) {
1969 if (IS_DEBUG_OSPF_NSSA)
1970 zlog_debug(
dc135f9e 1971 "%s: Could not originate Translated Type-5 for %pI4",
1972 __func__, &ei.p.prefix);
d62a17ae 1973 return NULL;
1974 }
1975
1976 extnew = (struct as_external_lsa *)(new->data);
1977
1978 /* copy over Type-7 data to new */
1979 extnew->e[0].tos = ext->e[0].tos;
1980 extnew->e[0].route_tag = ext->e[0].route_tag;
c317eddb 1981 if (type7->area->suppress_fa) {
1982 extnew->e[0].fwd_addr.s_addr = 0;
1983 if (IS_DEBUG_OSPF_NSSA)
e6f3b262 1984 zlog_debug("%s: Suppress forwarding address for %pI4",
1985 __func__, &ei.p.prefix);
c317eddb 1986 } else
1987 extnew->e[0].fwd_addr.s_addr = ext->e[0].fwd_addr.s_addr;
d62a17ae 1988 new->data->ls_seqnum = type7->data->ls_seqnum;
1989
1990 /* add translated flag, checksum and lock new lsa */
1991 SET_FLAG(new->flags, OSPF_LSA_LOCAL_XLT); /* Translated from 7 */
1992 new = ospf_lsa_lock(new);
1993
1994 return new;
d4a53d58 1995}
1996
d4a53d58 1997/* Originate Translated Type-5 for supplied Type-7 NSSA LSA */
d62a17ae 1998struct ospf_lsa *ospf_translated_nssa_originate(struct ospf *ospf,
c317eddb 1999 struct ospf_lsa *type7,
2000 struct ospf_lsa *type5)
d62a17ae 2001{
2002 struct ospf_lsa *new;
2003 struct as_external_lsa *extnew;
2004
10514170
RW
2005 if (ospf->gr_info.restart_in_progress) {
2006 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
2007 zlog_debug(
2008 "LSA[Translated Type5]: Graceful Restart in progress, don't originate");
2009 return NULL;
2010 }
2011
d62a17ae 2012 /* we cant use ospf_external_lsa_originate() as we need to set
2013 * the OSPF_LSA_LOCAL_XLT flag, must originate by hand
2014 */
2015
2016 if ((new = ospf_lsa_translated_nssa_new(ospf, type7)) == NULL) {
2017 if (IS_DEBUG_OSPF_NSSA)
2018 zlog_debug(
dc135f9e 2019 "%s: Could not translate Type-7, Id %pI4, to Type-5",
2020 __func__, &type7->data->id);
d62a17ae 2021 return NULL;
2022 }
2023
919714bd 2024 extnew = (struct as_external_lsa *)new->data;
2025
c317eddb 2026 /* Update LSA sequence number from translated Type-5 LSA */
2027 if (type5)
2028 new->data->ls_seqnum = lsa_seqnum_increment(type5);
2029
919714bd 2030 if ((new = ospf_lsa_install(ospf, NULL, new)) == NULL) {
dc135f9e 2031 flog_warn(EC_OSPF_LSA_INSTALL_FAILURE,
2032 "%s: Could not install LSA id %pI4", __func__,
2033 &type7->data->id);
919714bd 2034 return NULL;
2035 }
d62a17ae 2036
2037 if (IS_DEBUG_OSPF_NSSA) {
dc135f9e 2038 zlog_debug("%s: translated Type 7, installed", __func__);
d62a17ae 2039 ospf_lsa_header_dump(new->data);
2040 zlog_debug(" Network mask: %d", ip_masklen(extnew->mask));
96b663a3
MS
2041 zlog_debug(" Forward addr: %pI4",
2042 &extnew->e[0].fwd_addr);
d62a17ae 2043 }
2044
d62a17ae 2045 ospf->lsa_originate_count++;
2046 ospf_flood_through_as(ospf, NULL, new);
2047
2048 return new;
d4a53d58 2049}
2050
2051/* Refresh Translated from NSSA AS-external-LSA. */
d62a17ae 2052struct ospf_lsa *ospf_translated_nssa_refresh(struct ospf *ospf,
2053 struct ospf_lsa *type7,
2054 struct ospf_lsa *type5)
2055{
2056 struct ospf_lsa *new = NULL;
c317eddb 2057 struct as_external_lsa *extold = NULL;
2058 uint32_t ls_seqnum = 0;
d62a17ae 2059
2060 /* Sanity checks. */
2061 assert(type7 || type5);
2062 if (!(type7 || type5))
2063 return NULL;
2064 if (type7)
2065 assert(type7->data);
2066 if (type5)
2067 assert(type5->data);
2068 assert(ospf->anyNSSA);
2069
2070 /* get required data according to what has been given */
2071 if (type7 && type5 == NULL) {
2072 /* find the translated Type-5 for this Type-7 */
2073 struct as_external_lsa *ext =
2074 (struct as_external_lsa *)(type7->data);
2075 struct prefix_ipv4 p = {
2076 .prefix = type7->data->id,
2077 .prefixlen = ip_masklen(ext->mask),
2078 .family = AF_INET,
2079 };
2080
2081 type5 = ospf_external_info_find_lsa(ospf, &p);
2082 } else if (type5 && type7 == NULL) {
2083 /* find the type-7 from which supplied type-5 was translated,
2084 * ie find first type-7 with same LSA Id.
2085 */
2086 struct listnode *ln, *lnn;
2087 struct route_node *rn;
2088 struct ospf_lsa *lsa;
2089 struct ospf_area *area;
2090
2091 for (ALL_LIST_ELEMENTS(ospf->areas, ln, lnn, area)) {
2092 if (area->external_routing != OSPF_AREA_NSSA && !type7)
2093 continue;
2094
044506e7 2095 LSDB_LOOP (NSSA_LSDB(area), rn, lsa) {
d62a17ae 2096 if (lsa->data->id.s_addr
2097 == type5->data->id.s_addr) {
2098 type7 = lsa;
2099 break;
2100 }
2101 }
2102 }
2103 }
2104
2105 /* do we have type7? */
2106 if (!type7) {
2107 if (IS_DEBUG_OSPF_NSSA)
e6f3b262 2108 zlog_debug("%s: no Type-7 found for Type-5 LSA Id %pI4",
2109 __func__, &type5->data->id);
d62a17ae 2110 return NULL;
2111 }
2112
2113 /* do we have valid translated type5? */
2114 if (type5 == NULL || !CHECK_FLAG(type5->flags, OSPF_LSA_LOCAL_XLT)) {
2115 if (IS_DEBUG_OSPF_NSSA)
2116 zlog_debug(
e6f3b262 2117 "%s: No translated Type-5 found for Type-7 with Id %pI4",
2118 __func__, &type7->data->id);
d62a17ae 2119 return NULL;
2120 }
2121
c317eddb 2122 extold = (struct as_external_lsa *)type5->data;
2123 if (type7->area->suppress_fa == 1) {
2124 if (extold->e[0].fwd_addr.s_addr == 0)
2125 ls_seqnum = ntohl(type5->data->ls_seqnum);
2126 }
2127
d62a17ae 2128 /* Delete LSA from neighbor retransmit-list. */
2129 ospf_ls_retransmit_delete_nbr_as(ospf, type5);
2130
2131 /* create new translated LSA */
2132 if ((new = ospf_lsa_translated_nssa_new(ospf, type7)) == NULL) {
2133 if (IS_DEBUG_OSPF_NSSA)
2134 zlog_debug(
e6f3b262 2135 "%s: Could not translate Type-7 for %pI4 to Type-5",
2136 __func__, &type7->data->id);
d62a17ae 2137 return NULL;
2138 }
2139
c317eddb 2140 if (type7->area->suppress_fa == 1) {
2141 if (extold->e[0].fwd_addr.s_addr == 0)
2142 new->data->ls_seqnum = htonl(ls_seqnum + 1);
2143 }
2144
d62a17ae 2145 if (!(new = ospf_lsa_install(ospf, NULL, new))) {
e6f3b262 2146 flog_warn(EC_OSPF_LSA_INSTALL_FAILURE,
2147 "%s: Could not install translated LSA, Id %pI4",
2148 __func__, &type7->data->id);
d62a17ae 2149 return NULL;
2150 }
2151
2152 /* Flood LSA through area. */
2153 ospf_flood_through_as(ospf, NULL, new);
2154
2155 return new;
2156}
2157
718e3744 2158/* Originate an AS-external-LSA, install and flood. */
d62a17ae 2159struct ospf_lsa *ospf_external_lsa_originate(struct ospf *ospf,
2160 struct external_info *ei)
2161{
2162 struct ospf_lsa *new;
2163
10514170
RW
2164 if (ospf->gr_info.restart_in_progress) {
2165 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
2166 zlog_debug(
2167 "LSA[Type5]: Graceful Restart in progress, don't originate");
2168 return NULL;
2169 }
2170
d62a17ae 2171 /* Added for NSSA project....
2172
2173 External LSAs are originated in ASBRs as usual, but for NSSA
2174 systems.
2175 there is the global Type-5 LSDB and a Type-7 LSDB installed for
2176 every area. The Type-7's are flooded to every IR and every ABR; We
2177 install the Type-5 LSDB so that the normal "refresh" code operates
2178 as usual, and flag them as not used during ASE calculations. The
2179 Type-7 LSDB is used for calculations. Each Type-7 has a Forwarding
2180 Address of non-zero.
2181
2182 If an ABR is the elected NSSA translator, following SPF and during
2183 the ABR task it will translate all the scanned Type-7's, with P-bit
2184 ON and not-self generated, and translate to Type-5's throughout the
2185 non-NSSA/STUB AS.
2186
2187 A difference in operation depends whether this ASBR is an ABR
2188 or not. If not an ABR, the P-bit is ON, to indicate that any
2189 elected NSSA-ABR can perform its translation.
2190
2191 If an ABR, the P-bit is OFF; No ABR will perform translation and
2192 this ASBR will flood the Type-5 LSA as usual.
2193
2194 For the case where this ASBR is not an ABR, the ASE calculations
2195 are based on the Type-5 LSDB; The Type-7 LSDB exists just to
2196 demonstrate to the user that there are LSA's that belong to any
2197 attached NSSA.
2198
2199 Finally, it just so happens that when the ABR is translating every
2200 Type-7 into Type-5, it installs it into the Type-5 LSDB as an
2201 approved Type-5 (translated from Type-7); at the end of translation
2202 if any Translated Type-5's remain unapproved, then they must be
2203 flushed from the AS.
2204
2205 */
2206
975a328e 2207 if (ospf->router_id.s_addr == INADDR_ANY) {
e5309c1a 2208 if (ei && IS_DEBUG_OSPF_EVENT)
975a328e
DA
2209 zlog_debug(
2210 "LSA[Type5:%pI4]: deferring AS-external-LSA origination, router ID is zero",
2211 &ei->p.prefix);
f1cf5af6
DL
2212 return NULL;
2213 }
2214
d62a17ae 2215 /* Create new AS-external-LSA instance. */
2216 if ((new = ospf_external_lsa_new(ospf, ei, NULL)) == NULL) {
e5309c1a 2217 if (ei && IS_DEBUG_OSPF_EVENT)
d62a17ae 2218 zlog_debug(
96b663a3
MS
2219 "LSA[Type5:%pI4]: Could not originate AS-external-LSA",
2220 &ei->p.prefix);
d62a17ae 2221 return NULL;
2222 }
2223
2224 /* Install newly created LSA into Type-5 LSDB, lock = 1. */
2225 ospf_lsa_install(ospf, NULL, new);
2226
2227 /* Update LSA origination count. */
2228 ospf->lsa_originate_count++;
2229
2230 /* Flooding new LSA. only to AS (non-NSSA/STUB) */
2231 ospf_flood_through_as(ospf, NULL, new);
2232
2233 /* If there is any attached NSSA, do special handling */
2234 if (ospf->anyNSSA &&
2235 /* stay away from translated LSAs! */
2236 !(CHECK_FLAG(new->flags, OSPF_LSA_LOCAL_XLT)))
2237 ospf_install_flood_nssa(
2238 ospf, new, ei); /* Install/Flood Type-7 to all NSSAs */
2239
2240 /* Debug logging. */
2241 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
2242 zlog_debug("LSA[Type%d:%pI4]: Originate AS-external-LSA %p",
2243 new->data->type, &new->data->id,
d62a17ae 2244 (void *)new);
2245 ospf_lsa_header_dump(new->data);
2246 }
2247
2248 return new;
718e3744 2249}
2250
d62a17ae 2251static struct external_info *ospf_default_external_info(struct ospf *ospf)
2252{
2253 int type;
d62a17ae 2254 struct prefix_ipv4 p;
1febb13d
S
2255 struct external_info *default_ei;
2256 int ret = 0;
d62a17ae 2257
2258 p.family = AF_INET;
2259 p.prefix.s_addr = 0;
2260 p.prefixlen = 0;
2261
ffa484b4 2262 default_ei = ospf_external_info_lookup(ospf, DEFAULT_ROUTE, 0, &p);
1febb13d
S
2263 if (!default_ei)
2264 return NULL;
2265
d62a17ae 2266 /* First, lookup redistributed default route. */
2267 for (type = 0; type <= ZEBRA_ROUTE_MAX; type++) {
2268 struct list *ext_list;
d62a17ae 2269
2270 if (type == ZEBRA_ROUTE_OSPF)
2271 continue;
2272
de1ac5fd 2273 ext_list = ospf->external[type];
d62a17ae 2274 if (!ext_list)
2275 continue;
2276
1febb13d
S
2277 ret = ospf_external_default_routemap_apply_walk(ospf, ext_list,
2278 default_ei);
2279 if (ret)
2280 return default_ei;
d62a17ae 2281 }
2282
2283 return NULL;
2284}
2285
fa3c7c7e 2286void ospf_external_lsa_rid_change(struct ospf *ospf)
d62a17ae 2287{
d62a17ae 2288 struct external_info *ei;
960417cf 2289 struct ospf_external_aggr_rt *aggr;
a4d9009d 2290 struct ospf_lsa *lsa = NULL;
2291 int force;
fa3c7c7e 2292 int type;
d62a17ae 2293
fa3c7c7e
DL
2294 for (type = 0; type < ZEBRA_ROUTE_MAX; type++) {
2295 struct route_node *rn;
2296 struct route_table *rt;
2297 struct list *ext_list;
2298 struct listnode *node;
2299 struct ospf_external *ext;
d62a17ae 2300
fa3c7c7e
DL
2301 ext_list = ospf->external[type];
2302 if (!ext_list)
2303 continue;
d62a17ae 2304
fa3c7c7e
DL
2305 for (ALL_LIST_ELEMENTS_RO(ext_list, node, ext)) {
2306 /* Originate As-external-LSA from all type of
2307 * distribute source.
2308 */
2309 rt = ext->external_info;
2310 if (!rt)
2311 continue;
d62a17ae 2312
fa3c7c7e
DL
2313 for (rn = route_top(rt); rn; rn = route_next(rn)) {
2314 ei = rn->info;
d62a17ae 2315
fa3c7c7e
DL
2316 if (!ei)
2317 continue;
2318
1fe59b44 2319 if (is_default_prefix4(&ei->p))
fa3c7c7e
DL
2320 continue;
2321
a4d9009d 2322 lsa = ospf_external_info_find_lsa(ospf, &ei->p);
960417cf 2323
2324 aggr = ospf_external_aggr_match(ospf, &ei->p);
2325 if (aggr) {
a4d9009d 2326
2327 if (!ospf_redistribute_check(ospf, ei,
2328 NULL))
2329 continue;
2330
960417cf 2331 if (IS_DEBUG_OSPF(lsa, EXTNL_LSA_AGGR))
2332 zlog_debug(
2333 "Originate Summary LSA after reset/router-ID change");
a4d9009d 2334
960417cf 2335 /* Here the LSA is originated as new */
2336 ospf_originate_summary_lsa(ospf, aggr,
2337 ei);
a4d9009d 2338 } else if (lsa) {
2339 /* LSA needs to be refreshed even if
2340 * there is no change in the route
2341 * params if the LSA is in maxage.
2342 */
2343 if (IS_LSA_MAXAGE(lsa))
2344 force = LSA_REFRESH_FORCE;
2345 else
2346 force = LSA_REFRESH_IF_CHANGED;
2347
2348 ospf_external_lsa_refresh(ospf, lsa,
2349 ei, force, 0);
2350 } else {
2351 if (!ospf_redistribute_check(ospf, ei,
2352 NULL))
2353 continue;
2354
2355 if (!ospf_external_lsa_originate(ospf,
c1624189 2356 ei))
a4d9009d 2357 flog_warn(
2358 EC_OSPF_LSA_INSTALL_FAILURE,
2359 "LSA: AS-external-LSA was not originated.");
2360 }
fa3c7c7e
DL
2361 }
2362 }
2363 }
2364
2365 ei = ospf_default_external_info(ospf);
2366 if (ei && !ospf_external_lsa_originate(ospf, ei)) {
2367 flog_warn(EC_OSPF_LSA_INSTALL_FAILURE,
2368 "LSA: AS-external-LSA for default route was not originated.");
2369 }
718e3744 2370}
2371
645878f1 2372/* Flush any NSSA LSAs for given prefix */
d62a17ae 2373void ospf_nssa_lsa_flush(struct ospf *ospf, struct prefix_ipv4 *p)
2374{
2375 struct listnode *node, *nnode;
b5a8894d 2376 struct ospf_lsa *lsa = NULL;
d62a17ae 2377 struct ospf_area *area;
2378
2379 for (ALL_LIST_ELEMENTS(ospf->areas, node, nnode, area)) {
2380 if (area->external_routing == OSPF_AREA_NSSA) {
996c9314
LB
2381 lsa = ospf_lsa_lookup(ospf, area, OSPF_AS_NSSA_LSA,
2382 p->prefix, ospf->router_id);
b5a8894d 2383 if (!lsa) {
d62a17ae 2384 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
2385 zlog_debug(
ae32e1c2
DS
2386 "LSA: There is no such AS-NSSA-LSA %pFX in LSDB",
2387 p);
d62a17ae 2388 continue;
2389 }
2390 ospf_ls_retransmit_delete_nbr_area(area, lsa);
2391 if (!IS_LSA_MAXAGE(lsa)) {
2392 ospf_refresher_unregister_lsa(ospf, lsa);
2393 ospf_lsa_flush_area(lsa, area);
2394 }
2395 }
2396 }
645878f1 2397}
645878f1 2398
718e3744 2399/* Flush an AS-external-LSA from LSDB and routing domain. */
d7c0a89a 2400void ospf_external_lsa_flush(struct ospf *ospf, uint8_t type,
d62a17ae 2401 struct prefix_ipv4 *p,
2402 ifindex_t ifindex /*, struct in_addr nexthop */)
2403{
2404 struct ospf_lsa *lsa;
2405
2406 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
ae32e1c2 2407 zlog_debug("LSA: Flushing AS-external-LSA %pFX", p);
d62a17ae 2408
2409 /* First lookup LSA from LSDB. */
2410 if (!(lsa = ospf_external_info_find_lsa(ospf, p))) {
2411 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
2412 zlog_debug(
ae32e1c2
DS
2413 "LSA: There is no such AS-external-LSA %pFX in LSDB",
2414 p);
d62a17ae 2415 return;
2416 }
2417
2418 /* If LSA is selforiginated, not a translated LSA, and there is
2419 * NSSA area, flush Type-7 LSA's at first.
2420 */
2421 if (IS_LSA_SELF(lsa) && (ospf->anyNSSA)
2422 && !(CHECK_FLAG(lsa->flags, OSPF_LSA_LOCAL_XLT)))
2423 ospf_nssa_lsa_flush(ospf, p);
2424
d62a17ae 2425 if (!IS_LSA_MAXAGE(lsa)) {
ab31275c 2426 /* Sweep LSA from Link State Retransmit List. */
2427 ospf_ls_retransmit_delete_nbr_as(ospf, lsa);
2428
d62a17ae 2429 /* Unregister LSA from Refresh queue. */
2430 ospf_refresher_unregister_lsa(ospf, lsa);
2431
2432 /* Flush AS-external-LSA through AS. */
2433 ospf_lsa_flush_as(ospf, lsa);
2434 }
2435
2436 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
e6f3b262 2437 zlog_debug("%s: stop", __func__);
d62a17ae 2438}
2439
2440void ospf_external_lsa_refresh_default(struct ospf *ospf)
2441{
2442 struct prefix_ipv4 p;
2443 struct external_info *ei;
2444 struct ospf_lsa *lsa;
2445
2446 p.family = AF_INET;
2447 p.prefixlen = 0;
975a328e 2448 p.prefix.s_addr = INADDR_ANY;
d62a17ae 2449
2450 ei = ospf_default_external_info(ospf);
2451 lsa = ospf_external_info_find_lsa(ospf, &p);
2452
d5eac1e0
DL
2453 if (ei && lsa) {
2454 if (IS_DEBUG_OSPF_EVENT)
2455 zlog_debug("LSA[Type5:0.0.0.0]: Refresh AS-external-LSA %p",
63f0e941 2456 (void *)lsa);
2457 ospf_external_lsa_refresh(ospf, lsa, ei, LSA_REFRESH_FORCE,
2458 false);
d5eac1e0
DL
2459 } else if (ei && !lsa) {
2460 if (IS_DEBUG_OSPF_EVENT)
2461 zlog_debug(
2462 "LSA[Type5:0.0.0.0]: Originate AS-external-LSA");
2463 ospf_external_lsa_originate(ospf, ei);
2464 } else if (lsa) {
2465 if (IS_DEBUG_OSPF_EVENT)
2466 zlog_debug("LSA[Type5:0.0.0.0]: Flush AS-external-LSA");
2467 ospf_external_lsa_flush(ospf, DEFAULT_ROUTE, &p, 0);
d62a17ae 2468 }
2469}
2470
d7c0a89a
QY
2471void ospf_external_lsa_refresh_type(struct ospf *ospf, uint8_t type,
2472 unsigned short instance, int force)
d62a17ae 2473{
2474 struct route_node *rn;
2475 struct external_info *ei;
2476 struct ospf_external *ext;
2477
de1ac5fd
CS
2478 if (type == DEFAULT_ROUTE)
2479 return;
2480
2481 ext = ospf_external_lookup(ospf, type, instance);
2482
2483 if (ext && EXTERNAL_INFO(ext)) {
2484 /* Refresh each redistributed AS-external-LSAs. */
2485 for (rn = route_top(EXTERNAL_INFO(ext)); rn;
2486 rn = route_next(rn)) {
2487 ei = rn->info;
2488 if (ei) {
1fe59b44 2489 if (!is_default_prefix4(&ei->p)) {
de1ac5fd 2490 struct ospf_lsa *lsa;
960417cf 2491 struct ospf_external_aggr_rt *aggr;
de1ac5fd 2492
960417cf 2493 aggr = ospf_external_aggr_match(ospf,
2494 &ei->p);
996c9314 2495 lsa = ospf_external_info_find_lsa(
960417cf 2496 ospf, &ei->p);
2497 if (aggr) {
2498 /* Check the AS-external-LSA
2499 * should be originated.
2500 */
2501 if (!ospf_redistribute_check(
2502 ospf, ei, NULL)) {
2503
2504 ospf_unlink_ei_from_aggr(
2505 ospf, aggr, ei);
2506 continue;
2507 }
2508
2509 if (IS_DEBUG_OSPF(
2510 lsa,
2511 EXTNL_LSA_AGGR))
2512 zlog_debug(
f1db813d 2513 "%s: Send Aggreate LSA (%pFX)",
960417cf 2514 __func__,
f1db813d 2515 &aggr->p);
960417cf 2516
2517 ospf_originate_summary_lsa(
2518 ospf, aggr, ei);
2519
2520 } else if (lsa) {
2521
2522 if (IS_LSA_MAXAGE(lsa))
2523 force = LSA_REFRESH_FORCE;
2524
996c9314 2525 ospf_external_lsa_refresh(
63f0e941 2526 ospf, lsa, ei, force,
2527 false);
960417cf 2528 } else {
2529 if (!ospf_redistribute_check(
2530 ospf, ei, NULL))
2531 continue;
996c9314
LB
2532 ospf_external_lsa_originate(
2533 ospf, ei);
960417cf 2534 }
de1ac5fd
CS
2535 }
2536 }
2537 }
2538 }
718e3744 2539}
2540
2541/* Refresh AS-external-LSA. */
d62a17ae 2542struct ospf_lsa *ospf_external_lsa_refresh(struct ospf *ospf,
2543 struct ospf_lsa *lsa,
63f0e941 2544 struct external_info *ei, int force,
2545 bool is_aggr)
d62a17ae 2546{
2547 struct ospf_lsa *new;
63f0e941 2548 int changed = 0;
d62a17ae 2549
2550 /* Check the AS-external-LSA should be originated. */
63f0e941 2551 if (!is_aggr)
2552 if (!ospf_redistribute_check(ospf, ei, &changed)) {
2553 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
2554 zlog_debug(
ce513ac6 2555 "LSA[Type%d:%pI4] Could not be refreshed, redist check fail",
63f0e941 2556 lsa->data->type,
ce513ac6 2557 &lsa->data->id);
63f0e941 2558
2559 ospf_external_lsa_flush(ospf, ei->type, &ei->p,
2560 ei->ifindex /*, ei->nexthop */);
2561 return NULL;
2562 }
d62a17ae 2563
2564 if (!changed && !force) {
2565 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
2566 zlog_debug(
96b663a3
MS
2567 "LSA[Type%d:%pI4]: Not refreshed, not changed/forced",
2568 lsa->data->type, &lsa->data->id);
d62a17ae 2569 return NULL;
2570 }
2571
2572 /* Delete LSA from neighbor retransmit-list. */
2573 ospf_ls_retransmit_delete_nbr_as(ospf, lsa);
2574
2575 /* Unregister AS-external-LSA from refresh-list. */
2576 ospf_refresher_unregister_lsa(ospf, lsa);
2577
2578 new = ospf_external_lsa_new(ospf, ei, &lsa->data->id);
2579
2580 if (new == NULL) {
2581 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
96b663a3
MS
2582 zlog_debug("LSA[Type%d:%pI4]: Could not be refreshed",
2583 lsa->data->type, &lsa->data->id);
d62a17ae 2584 return NULL;
2585 }
2586
2587 new->data->ls_seqnum = lsa_seqnum_increment(lsa);
2588
2589 ospf_lsa_install(ospf, NULL, new); /* As type-5. */
2590
2591 /* Flood LSA through AS. */
2592 ospf_flood_through_as(ospf, NULL, new);
2593
2594 /* If any attached NSSA, install as Type-7, flood to all NSSA Areas */
2595 if (ospf->anyNSSA && !(CHECK_FLAG(new->flags, OSPF_LSA_LOCAL_XLT)))
2596 ospf_install_flood_nssa(ospf, new,
2597 ei); /* Install/Flood per new rules */
2598
2599 /* Register self-originated LSA to refresh queue.
2600 * Translated LSAs should not be registered, but refreshed upon
2601 * refresh of the Type-7
2602 */
2603 if (!CHECK_FLAG(new->flags, OSPF_LSA_LOCAL_XLT))
2604 ospf_refresher_register_lsa(ospf, new);
2605
2606 /* Debug logging. */
2607 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
96b663a3
MS
2608 zlog_debug("LSA[Type%d:%pI4]: AS-external-LSA refresh",
2609 new->data->type, &new->data->id);
d62a17ae 2610 ospf_lsa_header_dump(new->data);
2611 }
2612
2613 return new;
718e3744 2614}
2615
6b0655a2 2616
718e3744 2617/* LSA installation functions. */
2618
2619/* Install router-LSA to an area. */
4dadc291 2620static struct ospf_lsa *
d62a17ae 2621ospf_router_lsa_install(struct ospf *ospf, struct ospf_lsa *new, int rt_recalc)
718e3744 2622{
d62a17ae 2623 struct ospf_area *area = new->area;
718e3744 2624
d62a17ae 2625 /* RFC 2328 Section 13.2 Router-LSAs and network-LSAs
2626 The entire routing table must be recalculated, starting with
2627 the shortest path calculations for each area (not just the
2628 area whose link-state database has changed).
2629 */
718e3744 2630
d62a17ae 2631 if (IS_LSA_SELF(new)) {
5996e0df 2632
d62a17ae 2633 /* Only install LSA if it is originated/refreshed by us.
2634 * If LSA was received by flooding, the RECEIVED flag is set so
2635 * do
2636 * not link the LSA */
2637 if (CHECK_FLAG(new->flags, OSPF_LSA_RECEIVED))
2638 return new; /* ignore stale LSA */
5996e0df 2639
d62a17ae 2640 /* Set self-originated router-LSA. */
2641 ospf_lsa_unlock(&area->router_lsa_self);
2642 area->router_lsa_self = ospf_lsa_lock(new);
718e3744 2643
d62a17ae 2644 ospf_refresher_register_lsa(ospf, new);
2645 }
2646 if (rt_recalc)
2647 ospf_spf_calculate_schedule(ospf, SPF_FLAG_ROUTER_LSA_INSTALL);
2648 return new;
718e3744 2649}
2650
718e3744 2651/* Install network-LSA to an area. */
d62a17ae 2652static struct ospf_lsa *ospf_network_lsa_install(struct ospf *ospf,
2653 struct ospf_interface *oi,
2654 struct ospf_lsa *new,
2655 int rt_recalc)
2656{
3228977f 2657
d62a17ae 2658 /* RFC 2328 Section 13.2 Router-LSAs and network-LSAs
2659 The entire routing table must be recalculated, starting with
2660 the shortest path calculations for each area (not just the
2661 area whose link-state database has changed).
2662 */
2663 if (IS_LSA_SELF(new)) {
2664 /* We supposed that when LSA is originated by us, we pass the
2665 int
2666 for which it was originated. If LSA was received by flooding,
2667 the RECEIVED flag is set, so we do not link the LSA to the
2668 int. */
2669 if (CHECK_FLAG(new->flags, OSPF_LSA_RECEIVED))
2670 return new; /* ignore stale LSA */
2671
2672 ospf_lsa_unlock(&oi->network_lsa_self);
2673 oi->network_lsa_self = ospf_lsa_lock(new);
2674 ospf_refresher_register_lsa(ospf, new);
2675 }
2676 if (rt_recalc)
2677 ospf_spf_calculate_schedule(ospf, SPF_FLAG_NETWORK_LSA_INSTALL);
2678
2679 return new;
718e3744 2680}
2681
2682/* Install summary-LSA to an area. */
4dadc291 2683static struct ospf_lsa *
d62a17ae 2684ospf_summary_lsa_install(struct ospf *ospf, struct ospf_lsa *new, int rt_recalc)
2685{
2686 if (rt_recalc && !IS_LSA_SELF(new)) {
2687/* RFC 2328 Section 13.2 Summary-LSAs
2688 The best route to the destination described by the summary-
2689 LSA must be recalculated (see Section 16.5). If this
2690 destination is an AS boundary router, it may also be
2691 necessary to re-examine all the AS-external-LSAs.
2692*/
718e3744 2693
d62a17ae 2694 ospf_spf_calculate_schedule(ospf, SPF_FLAG_SUMMARY_LSA_INSTALL);
d62a17ae 2695 }
718e3744 2696
d62a17ae 2697 if (IS_LSA_SELF(new))
2698 ospf_refresher_register_lsa(ospf, new);
718e3744 2699
d62a17ae 2700 return new;
718e3744 2701}
2702
2703/* Install ASBR-summary-LSA to an area. */
d62a17ae 2704static struct ospf_lsa *ospf_summary_asbr_lsa_install(struct ospf *ospf,
2705 struct ospf_lsa *new,
2706 int rt_recalc)
2707{
2708 if (rt_recalc && !IS_LSA_SELF(new)) {
2709/* RFC 2328 Section 13.2 Summary-LSAs
2710 The best route to the destination described by the summary-
2711 LSA must be recalculated (see Section 16.5). If this
2712 destination is an AS boundary router, it may also be
2713 necessary to re-examine all the AS-external-LSAs.
2714*/
d62a17ae 2715 ospf_spf_calculate_schedule(ospf,
2716 SPF_FLAG_ASBR_SUMMARY_LSA_INSTALL);
d62a17ae 2717 }
718e3744 2718
d62a17ae 2719 /* register LSA to refresh-list. */
2720 if (IS_LSA_SELF(new))
2721 ospf_refresher_register_lsa(ospf, new);
718e3744 2722
d62a17ae 2723 return new;
718e3744 2724}
2725
2726/* Install AS-external-LSA. */
d62a17ae 2727static struct ospf_lsa *ospf_external_lsa_install(struct ospf *ospf,
2728 struct ospf_lsa *new,
2729 int rt_recalc)
2730{
2731 ospf_ase_register_external_lsa(new, ospf);
2732 /* If LSA is not self-originated, calculate an external route. */
2733 if (rt_recalc) {
2734 /* RFC 2328 Section 13.2 AS-external-LSAs
2735 The best route to the destination described by the AS-
2736 external-LSA must be recalculated (see Section 16.6).
2737 */
2738
2739 if (!IS_LSA_SELF(new))
2740 ospf_ase_incremental_update(ospf, new);
2741 }
2742
2743 if (new->data->type == OSPF_AS_NSSA_LSA) {
2744 /* There is no point to register selforiginate Type-7 LSA for
2745 * refreshing. We rely on refreshing Type-5 LSA's
2746 */
2747 if (IS_LSA_SELF(new))
2748 return new;
2749 else {
2750 /* Try refresh type-5 translated LSA for this LSA, if
2751 * one exists.
2752 * New translations will be taken care of by the
2753 * abr_task.
2754 */
2755 ospf_translated_nssa_refresh(ospf, new, NULL);
493472ba 2756 ospf_schedule_abr_task(ospf);
d62a17ae 2757 }
2758 }
2759
2760 /* Register self-originated LSA to refresh queue.
2761 * Leave Translated LSAs alone if NSSA is enabled
2762 */
2763 if (IS_LSA_SELF(new) && !CHECK_FLAG(new->flags, OSPF_LSA_LOCAL_XLT))
2764 ospf_refresher_register_lsa(ospf, new);
2765
2766 return new;
2767}
2768
2769void ospf_discard_from_db(struct ospf *ospf, struct ospf_lsdb *lsdb,
2770 struct ospf_lsa *lsa)
2771{
2772 struct ospf_lsa *old;
2773
266469eb 2774 if (!lsdb)
d62a17ae 2775 return;
d62a17ae 2776
2777 old = ospf_lsdb_lookup(lsdb, lsa);
2778
2779 if (!old)
2780 return;
2781
2782 if (old->refresh_list >= 0)
2783 ospf_refresher_unregister_lsa(ospf, old);
2784
2785 switch (old->data->type) {
2786 case OSPF_AS_EXTERNAL_LSA:
2787 ospf_ase_unregister_external_lsa(old, ospf);
2788 ospf_ls_retransmit_delete_nbr_as(ospf, old);
2789 break;
2790 case OSPF_OPAQUE_AS_LSA:
2791 ospf_ls_retransmit_delete_nbr_as(ospf, old);
2792 break;
2793 case OSPF_AS_NSSA_LSA:
2794 ospf_ls_retransmit_delete_nbr_area(old->area, old);
2795 ospf_ase_unregister_external_lsa(old, ospf);
2796 break;
2797 default:
2798 ospf_ls_retransmit_delete_nbr_area(old->area, old);
2799 break;
2800 }
2801
2802 ospf_lsa_maxage_delete(ospf, old);
2803 ospf_lsa_discard(old);
2804}
2805
2806struct ospf_lsa *ospf_lsa_install(struct ospf *ospf, struct ospf_interface *oi,
2807 struct ospf_lsa *lsa)
2808{
2809 struct ospf_lsa *new = NULL;
2810 struct ospf_lsa *old = NULL;
2811 struct ospf_lsdb *lsdb = NULL;
2812 int rt_recalc;
2813
2814 /* Set LSDB. */
2815 switch (lsa->data->type) {
2816 /* kevinm */
2817 case OSPF_AS_NSSA_LSA:
2818 if (lsa->area)
2819 lsdb = lsa->area->lsdb;
2820 else
2821 lsdb = ospf->lsdb;
2822 break;
2823 case OSPF_AS_EXTERNAL_LSA:
2824 case OSPF_OPAQUE_AS_LSA:
2825 lsdb = ospf->lsdb;
2826 break;
2827 default:
a37befa7 2828 if (lsa->area)
2829 lsdb = lsa->area->lsdb;
d62a17ae 2830 break;
2831 }
2832
2833 assert(lsdb);
2834
2835 /* RFC 2328 13.2. Installing LSAs in the database
2836
2837 Installing a new LSA in the database, either as the result of
2838 flooding or a newly self-originated LSA, may cause the OSPF
2839 routing table structure to be recalculated. The contents of the
2840 new LSA should be compared to the old instance, if present. If
2841 there is no difference, there is no need to recalculate the
2842 routing table. When comparing an LSA to its previous instance,
2843 the following are all considered to be differences in contents:
2844
2845 o The LSA's Options field has changed.
2846
2847 o One of the LSA instances has LS age set to MaxAge, and
2848 the other does not.
2849
2850 o The length field in the LSA header has changed.
2851
2852 o The body of the LSA (i.e., anything outside the 20-byte
2853 LSA header) has changed. Note that this excludes changes
2854 in LS Sequence Number and LS Checksum.
2855
2856 */
2857 /* Look up old LSA and determine if any SPF calculation or incremental
2858 update is needed */
2859 old = ospf_lsdb_lookup(lsdb, lsa);
2860
ce5002c6 2861 /* Do comparison and record if recalc needed. */
d62a17ae 2862 rt_recalc = 0;
1bb2674c 2863 if (old == NULL || ospf_lsa_different(old, lsa, false)) {
df074ec3 2864 /* Ref rfc3623 section 3.2.3
2865 * Installing new lsa or change in the existing LSA
2866 * or flushing existing LSA leads to topo change
2867 * and trigger SPF caculation.
2868 * So, router should be aborted from HELPER role
2869 * if it is detected as TOPO change.
2870 */
ef151af7 2871 if (ospf->active_restarter_cnt &&
2872 CHECK_LSA_TYPE_1_TO_5_OR_7(lsa->data->type)) {
2873 if (old == NULL || ospf_lsa_different(old, lsa, true))
2874 ospf_helper_handle_topo_chg(ospf, lsa);
2875 }
df074ec3 2876
d62a17ae 2877 rt_recalc = 1;
df074ec3 2878 }
d62a17ae 2879
2880 /*
2881 Sequence number check (Section 14.1 of rfc 2328)
2882 "Premature aging is used when it is time for a self-originated
2883 LSA's sequence number field to wrap. At this point, the current
2884 LSA instance (having LS sequence number MaxSequenceNumber) must
2885 be prematurely aged and flushed from the routing domain before a
2886 new instance with sequence number equal to InitialSequenceNumber
2887 can be originated. "
2888 */
2889
2890 if (ntohl(lsa->data->ls_seqnum) - 1 == OSPF_MAX_SEQUENCE_NUMBER) {
2891 if (ospf_lsa_is_self_originated(ospf, lsa)) {
2892 lsa->data->ls_seqnum = htonl(OSPF_MAX_SEQUENCE_NUMBER);
2893
2894 if (!IS_LSA_MAXAGE(lsa))
2895 lsa->flags |= OSPF_LSA_PREMATURE_AGE;
2896 lsa->data->ls_age = htons(OSPF_LSA_MAXAGE);
2897
2898 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH)) {
2899 zlog_debug(
461d106d
RW
2900 "%s() Premature Aging lsa %p, seqnum 0x%x",
2901 __func__, lsa,
d62a17ae 2902 ntohl(lsa->data->ls_seqnum));
2903 ospf_lsa_header_dump(lsa->data);
2904 }
2905 } else {
2906 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE)) {
2907 zlog_debug(
461d106d
RW
2908 "%s() got an lsa with seq 0x80000000 that was not self originated. Ignoring",
2909 __func__);
d62a17ae 2910 ospf_lsa_header_dump(lsa->data);
2911 }
2912 return old;
2913 }
2914 }
2915
2916 /* discard old LSA from LSDB */
2917 if (old != NULL)
2918 ospf_discard_from_db(ospf, lsdb, lsa);
2919
2920 /* Calculate Checksum if self-originated?. */
2921 if (IS_LSA_SELF(lsa))
2922 ospf_lsa_checksum(lsa->data);
2923
2924 /* Insert LSA to LSDB. */
2925 ospf_lsdb_add(lsdb, lsa);
2926 lsa->lsdb = lsdb;
2927
2928 /* Do LSA specific installation process. */
2929 switch (lsa->data->type) {
2930 case OSPF_ROUTER_LSA:
2931 new = ospf_router_lsa_install(ospf, lsa, rt_recalc);
2932 break;
2933 case OSPF_NETWORK_LSA:
2934 assert(oi);
2935 new = ospf_network_lsa_install(ospf, oi, lsa, rt_recalc);
2936 break;
2937 case OSPF_SUMMARY_LSA:
2938 new = ospf_summary_lsa_install(ospf, lsa, rt_recalc);
2939 break;
2940 case OSPF_ASBR_SUMMARY_LSA:
2941 new = ospf_summary_asbr_lsa_install(ospf, lsa, rt_recalc);
2942 break;
2943 case OSPF_AS_EXTERNAL_LSA:
2944 new = ospf_external_lsa_install(ospf, lsa, rt_recalc);
2945 break;
2946 case OSPF_OPAQUE_LINK_LSA:
2947 if (IS_LSA_SELF(lsa))
2948 lsa->oi = oi; /* Specify outgoing ospf-interface for
2949 this LSA. */
2950 else {
2951 /* Incoming "oi" for this LSA has set at LSUpd
2952 * reception. */
2953 }
2954 /* Fallthrough */
2955 case OSPF_OPAQUE_AREA_LSA:
2956 case OSPF_OPAQUE_AS_LSA:
2957 new = ospf_opaque_lsa_install(lsa, rt_recalc);
2958 break;
2959 case OSPF_AS_NSSA_LSA:
2960 new = ospf_external_lsa_install(ospf, lsa, rt_recalc);
2961 default: /* type-6,8,9....nothing special */
2962 break;
2963 }
2964
2965 if (new == NULL)
2966 return new; /* Installation failed, cannot proceed further --
2967 endo. */
2968
2969 /* Debug logs. */
2970 if (IS_DEBUG_OSPF(lsa, LSA_INSTALL)) {
d62a17ae 2971 switch (lsa->data->type) {
2972 case OSPF_AS_EXTERNAL_LSA:
2973 case OSPF_OPAQUE_AS_LSA:
2974 case OSPF_AS_NSSA_LSA:
2975 zlog_debug("LSA[%s]: Install %s", dump_lsa_key(new),
2976 lookup_msg(ospf_lsa_type_msg,
2977 new->data->type, NULL));
2978 break;
2979 default:
96b663a3 2980 zlog_debug("LSA[%s]: Install %s to Area %pI4",
d62a17ae 2981 dump_lsa_key(new),
2982 lookup_msg(ospf_lsa_type_msg,
2983 new->data->type, NULL),
96b663a3 2984 &new->area->area_id);
d62a17ae 2985 break;
2986 }
2987 }
2988
2989 /*
2990 If received LSA' ls_age is MaxAge, or lsa is being prematurely aged
2991 (it's getting flushed out of the area), set LSA on MaxAge LSA list.
2992 */
2993 if (IS_LSA_MAXAGE(new)) {
2994 if (IS_DEBUG_OSPF(lsa, LSA_INSTALL))
e9505bc6
RW
2995 zlog_debug("LSA[%s]: Install LSA %p, MaxAge",
2996 dump_lsa_key(new), lsa);
d62a17ae 2997 ospf_lsa_maxage(ospf, lsa);
2998 }
2999
3000 return new;
3001}
3002
3003
3004int ospf_check_nbr_status(struct ospf *ospf)
3005{
3006 struct listnode *node, *nnode;
3007 struct ospf_interface *oi;
3008
3009 for (ALL_LIST_ELEMENTS(ospf->oiflist, node, nnode, oi)) {
3010 struct route_node *rn;
3011 struct ospf_neighbor *nbr;
3012
3013 if (ospf_if_is_enable(oi))
3014 for (rn = route_top(oi->nbrs); rn; rn = route_next(rn))
3015 if ((nbr = rn->info) != NULL)
3016 if (nbr->state == NSM_Exchange
3017 || nbr->state == NSM_Loading) {
3018 route_unlock_node(rn);
3019 return 0;
3020 }
3021 }
3022
3023 return 1;
3024}
3025
3026
b345a3d9 3027void ospf_maxage_lsa_remover(struct thread *thread)
d62a17ae 3028{
3029 struct ospf *ospf = THREAD_ARG(thread);
f91ce319 3030 struct ospf_lsa *lsa, *old;
d62a17ae 3031 struct route_node *rn;
3032 int reschedule = 0;
3033
3034 ospf->t_maxage = NULL;
3035
3036 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3037 zlog_debug("LSA[MaxAge]: remover Start");
3038
3039 reschedule = !ospf_check_nbr_status(ospf);
3040
3041 if (!reschedule)
3042 for (rn = route_top(ospf->maxage_lsa); rn;
3043 rn = route_next(rn)) {
3044 if ((lsa = rn->info) == NULL) {
3045 continue;
3046 }
3047
3048 /* There is at least one neighbor from which we still
3049 * await an ack
3050 * for that LSA, so we are not allowed to remove it from
3051 * our lsdb yet
3052 * as per RFC 2328 section 14 para 4 a) */
3053 if (lsa->retransmit_counter > 0) {
3054 reschedule = 1;
3055 continue;
3056 }
3057
3058 /* TODO: maybe convert this function to a work-queue */
3059 if (thread_should_yield(thread)) {
3060 OSPF_TIMER_ON(ospf->t_maxage,
3061 ospf_maxage_lsa_remover, 0);
3062 route_unlock_node(
3063 rn); /* route_top/route_next */
cc9f21da 3064 return;
d62a17ae 3065 }
3066
3067 /* Remove LSA from the LSDB */
3068 if (IS_LSA_SELF(lsa))
3069 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3070 zlog_debug(
96b663a3 3071 "LSA[Type%d:%pI4]: LSA 0x%lx is self-originated: ",
d62a17ae 3072 lsa->data->type,
96b663a3 3073 &lsa->data->id,
d7c0a89a 3074 (unsigned long)lsa);
d62a17ae 3075
3076 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3077 zlog_debug(
e9505bc6
RW
3078 "LSA[%s]: MaxAge LSA removed from list",
3079 dump_lsa_key(lsa));
d62a17ae 3080
3081 if (CHECK_FLAG(lsa->flags, OSPF_LSA_PREMATURE_AGE)) {
3082 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3083 zlog_debug(
461d106d
RW
3084 "originating new lsa for lsa %p",
3085 lsa);
d62a17ae 3086 ospf_lsa_refresh(ospf, lsa);
3087 }
3088
3089 /* Remove from lsdb. */
3090 if (lsa->lsdb) {
f91ce319
MR
3091 old = ospf_lsdb_lookup(lsa->lsdb, lsa);
3092 /* The max age LSA here must be the same
3093 * as the LSA in LSDB
3094 */
3095 if (old != lsa) {
3096 flog_err(EC_OSPF_LSA_MISSING,
e9505bc6
RW
3097 "%s: LSA[%s]: LSA not in LSDB",
3098 __func__, dump_lsa_key(lsa));
acc847c9 3099
f91ce319
MR
3100 continue;
3101 }
d62a17ae 3102 ospf_discard_from_db(ospf, lsa->lsdb, lsa);
3103 ospf_lsdb_delete(lsa->lsdb, lsa);
13ab4921
DS
3104 } else {
3105 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3106 zlog_debug(
e9505bc6
RW
3107 "%s: LSA[%s]: No associated LSDB!",
3108 __func__, dump_lsa_key(lsa));
13ab4921 3109 }
d62a17ae 3110 }
3111
3112 /* A MaxAge LSA must be removed immediately from the router's link
3113 state database as soon as both a) it is no longer contained on any
3114 neighbor Link state retransmission lists and b) none of the
3115 router's
3116 neighbors are in states Exchange or Loading. */
3117 if (reschedule)
3118 OSPF_TIMER_ON(ospf->t_maxage, ospf_maxage_lsa_remover,
3119 ospf->maxage_delay);
d62a17ae 3120}
3121
3cb62bb3
MR
3122/* This function checks whether an LSA with initial sequence number should be
3123 * originated after a wrap in sequence number
3124 */
3125void ospf_check_and_gen_init_seq_lsa(struct ospf_interface *oi,
3126 struct ospf_lsa *recv_lsa)
3127{
3128 struct ospf_lsa *lsa = NULL;
3129 struct ospf *ospf = oi->ospf;
3130
3131 lsa = ospf_lsa_lookup_by_header(oi->area, recv_lsa->data);
3132
3133 if ((lsa == NULL) || (!CHECK_FLAG(lsa->flags, OSPF_LSA_PREMATURE_AGE))
3134 || (lsa->retransmit_counter != 0)) {
3135 if (IS_DEBUG_OSPF(lsa, LSA))
3136 zlog_debug(
3137 "Do not generate LSA with initial seqence number.");
3138 return;
3139 }
3140
3141 ospf_lsa_maxage_delete(ospf, lsa);
3142
3143 lsa->data->ls_seqnum = lsa_seqnum_increment(lsa);
3144
3145 ospf_lsa_refresh(ospf, lsa);
3146}
3147
d62a17ae 3148void ospf_lsa_maxage_delete(struct ospf *ospf, struct ospf_lsa *lsa)
3149{
3150 struct route_node *rn;
dcc3ef87 3151 struct prefix lsa_prefix;
d62a17ae 3152
6006b807 3153 memset(&lsa_prefix, 0, sizeof(lsa_prefix));
abb1bf8d 3154 lsa_prefix.family = AF_UNSPEC;
dcc3ef87
CS
3155 lsa_prefix.prefixlen = sizeof(lsa_prefix.u.ptr) * CHAR_BIT;
3156 lsa_prefix.u.ptr = (uintptr_t)lsa;
d62a17ae 3157
c4efd0f4 3158 if ((rn = route_node_lookup(ospf->maxage_lsa, &lsa_prefix))) {
d62a17ae 3159 if (rn->info == lsa) {
3160 UNSET_FLAG(lsa->flags, OSPF_LSA_IN_MAXAGE);
3161 ospf_lsa_unlock(&lsa); /* maxage_lsa */
3162 rn->info = NULL;
3163 route_unlock_node(
3164 rn); /* unlock node because lsa is deleted */
3165 }
3166 route_unlock_node(rn); /* route_node_lookup */
dcc3ef87
CS
3167 } else {
3168 if (IS_DEBUG_OSPF_EVENT)
3169 zlog_debug("%s: lsa %s is not found in maxage db.",
15569c58 3170 __func__, dump_lsa_key(lsa));
d62a17ae 3171 }
718e3744 3172}
3173
02d942c9
PJ
3174/* Add LSA onto the MaxAge list, and schedule for removal.
3175 * This does *not* lead to the LSA being flooded, that must be taken
3176 * care of elsewhere, see, e.g., ospf_lsa_flush* (which are callers of this
3177 * function).
3178 */
d62a17ae 3179void ospf_lsa_maxage(struct ospf *ospf, struct ospf_lsa *lsa)
3180{
dcc3ef87 3181 struct prefix lsa_prefix;
d62a17ae 3182 struct route_node *rn;
3183
3184 /* When we saw a MaxAge LSA flooded to us, we put it on the list
3185 and schedule the MaxAge LSA remover. */
3186 if (CHECK_FLAG(lsa->flags, OSPF_LSA_IN_MAXAGE)) {
3187 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3188 zlog_debug(
e9505bc6
RW
3189 "LSA[%s]: %p already exists on MaxAge LSA list",
3190 dump_lsa_key(lsa), lsa);
d62a17ae 3191 return;
3192 }
3193
6006b807 3194 memset(&lsa_prefix, 0, sizeof(lsa_prefix));
abb1bf8d 3195 lsa_prefix.family = AF_UNSPEC;
dcc3ef87
CS
3196 lsa_prefix.prefixlen = sizeof(lsa_prefix.u.ptr) * CHAR_BIT;
3197 lsa_prefix.u.ptr = (uintptr_t)lsa;
d62a17ae 3198
c4efd0f4 3199 rn = route_node_get(ospf->maxage_lsa, &lsa_prefix);
0ce1ca80
DS
3200 if (rn->info != NULL) {
3201 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3202 zlog_debug(
3203 "LSA[%s]: found LSA (%p) in table for LSA %p %d",
3204 dump_lsa_key(lsa), rn->info,
3205 (void *)lsa, lsa_prefix.prefixlen);
3206 route_unlock_node(rn);
d62a17ae 3207 } else {
0ce1ca80
DS
3208 rn->info = ospf_lsa_lock(lsa);
3209 SET_FLAG(lsa->flags, OSPF_LSA_IN_MAXAGE);
d62a17ae 3210 }
3211
3212 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3213 zlog_debug("LSA[%s]: MaxAge LSA remover scheduled.",
3214 dump_lsa_key(lsa));
3215
3216 OSPF_TIMER_ON(ospf->t_maxage, ospf_maxage_lsa_remover,
3217 ospf->maxage_delay);
3218}
3219
3220static int ospf_lsa_maxage_walker_remover(struct ospf *ospf,
3221 struct ospf_lsa *lsa)
3222{
3223 /* Stay away from any Local Translated Type-7 LSAs */
3224 if (CHECK_FLAG(lsa->flags, OSPF_LSA_LOCAL_XLT))
3225 return 0;
3226
3227 if (IS_LSA_MAXAGE(lsa))
3228 /* Self-originated LSAs should NOT time-out instead,
3229 they're flushed and submitted to the max_age list explicitly.
3230 */
3231 if (!ospf_lsa_is_self_originated(ospf, lsa)) {
3232 if (IS_DEBUG_OSPF(lsa, LSA_FLOODING))
3233 zlog_debug("LSA[%s]: is MaxAge",
3234 dump_lsa_key(lsa));
3235
3236 switch (lsa->data->type) {
3237 case OSPF_OPAQUE_LINK_LSA:
3238 case OSPF_OPAQUE_AREA_LSA:
3239 case OSPF_OPAQUE_AS_LSA:
3240 /*
3241 * As a general rule, whenever network topology
3242 * has changed
3243 * (due to an LSA removal in this case), routing
3244 * recalculation
3245 * should be triggered. However, this is not
3246 * true for opaque
3247 * LSAs. Even if an opaque LSA instance is going
3248 * to be removed
3249 * from the routing domain, it does not mean a
3250 * change in network
3251 * topology, and thus, routing recalculation is
3252 * not needed here.
3253 */
3254 break;
3255 case OSPF_AS_EXTERNAL_LSA:
3256 case OSPF_AS_NSSA_LSA:
3257 ospf_ase_incremental_update(ospf, lsa);
3258 break;
3259 default:
3260 ospf_spf_calculate_schedule(ospf,
3261 SPF_FLAG_MAXAGE);
3262 break;
3263 }
3264 ospf_lsa_maxage(ospf, lsa);
3265 }
3266
3267 if (IS_LSA_MAXAGE(lsa) && !ospf_lsa_is_self_originated(ospf, lsa))
3268 if (LS_AGE(lsa) > OSPF_LSA_MAXAGE + 30)
3269 printf("Eek! Shouldn't happen!\n");
3270
3271 return 0;
718e3744 3272}
3273
3274/* Periodical check of MaxAge LSA. */
cc9f21da 3275void ospf_lsa_maxage_walker(struct thread *thread)
d62a17ae 3276{
3277 struct ospf *ospf = THREAD_ARG(thread);
3278 struct route_node *rn;
3279 struct ospf_lsa *lsa;
3280 struct ospf_area *area;
3281 struct listnode *node, *nnode;
3282
3283 ospf->t_maxage_walker = NULL;
3284
3285 for (ALL_LIST_ELEMENTS(ospf->areas, node, nnode, area)) {
996c9314 3286 LSDB_LOOP (ROUTER_LSDB(area), rn, lsa)
044506e7 3287 ospf_lsa_maxage_walker_remover(ospf, lsa);
996c9314 3288 LSDB_LOOP (NETWORK_LSDB(area), rn, lsa)
044506e7 3289 ospf_lsa_maxage_walker_remover(ospf, lsa);
996c9314 3290 LSDB_LOOP (SUMMARY_LSDB(area), rn, lsa)
044506e7 3291 ospf_lsa_maxage_walker_remover(ospf, lsa);
996c9314 3292 LSDB_LOOP (ASBR_SUMMARY_LSDB(area), rn, lsa)
044506e7 3293 ospf_lsa_maxage_walker_remover(ospf, lsa);
996c9314 3294 LSDB_LOOP (OPAQUE_AREA_LSDB(area), rn, lsa)
044506e7 3295 ospf_lsa_maxage_walker_remover(ospf, lsa);
996c9314 3296 LSDB_LOOP (OPAQUE_LINK_LSDB(area), rn, lsa)
044506e7 3297 ospf_lsa_maxage_walker_remover(ospf, lsa);
996c9314 3298 LSDB_LOOP (NSSA_LSDB(area), rn, lsa)
044506e7 3299 ospf_lsa_maxage_walker_remover(ospf, lsa);
d62a17ae 3300 }
3301
3302 /* for AS-external-LSAs. */
3303 if (ospf->lsdb) {
996c9314 3304 LSDB_LOOP (EXTERNAL_LSDB(ospf), rn, lsa)
044506e7 3305 ospf_lsa_maxage_walker_remover(ospf, lsa);
996c9314 3306 LSDB_LOOP (OPAQUE_AS_LSDB(ospf), rn, lsa)
044506e7 3307 ospf_lsa_maxage_walker_remover(ospf, lsa);
d62a17ae 3308 }
3309
3310 OSPF_TIMER_ON(ospf->t_maxage_walker, ospf_lsa_maxage_walker,
3311 OSPF_LSA_MAXAGE_CHECK_INTERVAL);
d62a17ae 3312}
3313
d7c0a89a 3314struct ospf_lsa *ospf_lsa_lookup_by_prefix(struct ospf_lsdb *lsdb, uint8_t type,
d62a17ae 3315 struct prefix_ipv4 *p,
3316 struct in_addr router_id)
3317{
3318 struct ospf_lsa *lsa;
3319 struct in_addr mask, id;
3320 struct lsa_header_mask {
3321 struct lsa_header header;
3322 struct in_addr mask;
3323 } * hmask;
3324
3325 lsa = ospf_lsdb_lookup_by_id(lsdb, type, p->prefix, router_id);
3326 if (lsa == NULL)
3327 return NULL;
3328
3329 masklen2ip(p->prefixlen, &mask);
3330
3331 hmask = (struct lsa_header_mask *)lsa->data;
3332
3333 if (mask.s_addr != hmask->mask.s_addr) {
3334 id.s_addr = p->prefix.s_addr | (~mask.s_addr);
3335 lsa = ospf_lsdb_lookup_by_id(lsdb, type, id, router_id);
3336 if (!lsa)
3337 return NULL;
3338 }
3339
3340 return lsa;
3341}
3342
b5a8894d 3343struct ospf_lsa *ospf_lsa_lookup(struct ospf *ospf, struct ospf_area *area,
d7c0a89a 3344 uint32_t type, struct in_addr id,
b5a8894d 3345 struct in_addr adv_router)
d62a17ae 3346{
b5a8894d
CS
3347 if (!ospf)
3348 return NULL;
d62a17ae 3349
3350 switch (type) {
3351 case OSPF_ROUTER_LSA:
3352 case OSPF_NETWORK_LSA:
3353 case OSPF_SUMMARY_LSA:
3354 case OSPF_ASBR_SUMMARY_LSA:
3355 case OSPF_AS_NSSA_LSA:
3356 case OSPF_OPAQUE_LINK_LSA:
3357 case OSPF_OPAQUE_AREA_LSA:
3358 return ospf_lsdb_lookup_by_id(area->lsdb, type, id, adv_router);
3359 case OSPF_AS_EXTERNAL_LSA:
3360 case OSPF_OPAQUE_AS_LSA:
3361 return ospf_lsdb_lookup_by_id(ospf->lsdb, type, id, adv_router);
3362 default:
3363 break;
3364 }
3365
3366 return NULL;
3367}
3368
d7c0a89a 3369struct ospf_lsa *ospf_lsa_lookup_by_id(struct ospf_area *area, uint32_t type,
d62a17ae 3370 struct in_addr id)
3371{
3372 struct ospf_lsa *lsa;
3373 struct route_node *rn;
3374
3375 switch (type) {
3376 case OSPF_ROUTER_LSA:
3377 return ospf_lsdb_lookup_by_id(area->lsdb, type, id, id);
3378 case OSPF_NETWORK_LSA:
3379 for (rn = route_top(NETWORK_LSDB(area)); rn;
3380 rn = route_next(rn))
3381 if ((lsa = rn->info))
3382 if (IPV4_ADDR_SAME(&lsa->data->id, &id)) {
3383 route_unlock_node(rn);
3384 return lsa;
3385 }
3386 break;
3387 case OSPF_SUMMARY_LSA:
3388 case OSPF_ASBR_SUMMARY_LSA:
3389 /* Currently not used. */
3390 assert(1);
3391 return ospf_lsdb_lookup_by_id(area->lsdb, type, id, id);
3392 case OSPF_AS_EXTERNAL_LSA:
3393 case OSPF_AS_NSSA_LSA:
3394 case OSPF_OPAQUE_LINK_LSA:
3395 case OSPF_OPAQUE_AREA_LSA:
3396 case OSPF_OPAQUE_AS_LSA:
3397 /* Currently not used. */
3398 break;
3399 default:
3400 break;
3401 }
3402
3403 return NULL;
3404}
3405
3406struct ospf_lsa *ospf_lsa_lookup_by_header(struct ospf_area *area,
3407 struct lsa_header *lsah)
3408{
3409 struct ospf_lsa *match;
3410
3411 /*
3412 * Strictly speaking, the LSA-ID field for Opaque-LSAs (type-9/10/11)
3413 * is redefined to have two subfields; opaque-type and opaque-id.
3414 * However, it is harmless to treat the two sub fields together, as if
3415 * they two were forming a unique LSA-ID.
3416 */
3417
b5a8894d
CS
3418 match = ospf_lsa_lookup(area->ospf, area, lsah->type, lsah->id,
3419 lsah->adv_router);
d62a17ae 3420
3421 if (match == NULL)
3422 if (IS_DEBUG_OSPF(lsa, LSA) == OSPF_DEBUG_LSA)
96b663a3
MS
3423 zlog_debug("LSA[Type%d:%pI4]: Lookup by header, NO MATCH",
3424 lsah->type, &lsah->id);
d62a17ae 3425
3426 return match;
718e3744 3427}
3428
3429/* return +n, l1 is more recent.
3430 return -n, l2 is more recent.
3431 return 0, l1 and l2 is identical. */
d62a17ae 3432int ospf_lsa_more_recent(struct ospf_lsa *l1, struct ospf_lsa *l2)
3433{
3434 int r;
3435 int x, y;
3436
3437 if (l1 == NULL && l2 == NULL)
3438 return 0;
3439 if (l1 == NULL)
3440 return -1;
3441 if (l2 == NULL)
3442 return 1;
3443
3444 /* compare LS sequence number. */
3445 x = (int)ntohl(l1->data->ls_seqnum);
3446 y = (int)ntohl(l2->data->ls_seqnum);
3447 if (x > y)
3448 return 1;
3449 if (x < y)
3450 return -1;
3451
3452 /* compare LS checksum. */
3453 r = ntohs(l1->data->checksum) - ntohs(l2->data->checksum);
3454 if (r)
3455 return r;
3456
3457 /* compare LS age. */
3458 if (IS_LSA_MAXAGE(l1) && !IS_LSA_MAXAGE(l2))
3459 return 1;
3460 else if (!IS_LSA_MAXAGE(l1) && IS_LSA_MAXAGE(l2))
3461 return -1;
3462
3463 /* compare LS age with MaxAgeDiff. */
3464 if (LS_AGE(l1) - LS_AGE(l2) > OSPF_LSA_MAXAGE_DIFF)
3465 return -1;
3466 else if (LS_AGE(l2) - LS_AGE(l1) > OSPF_LSA_MAXAGE_DIFF)
3467 return 1;
3468
3469 /* LSAs are identical. */
3470 return 0;
718e3744 3471}
3472
1bb2674c
RW
3473/*
3474 * Check if two LSAs are different.
3475 *
3476 * l1
3477 * The first LSA to compare.
3478 *
3479 * l2
3480 * The second LSA to compare.
3481 *
3482 * ignore_rcvd_flag
3483 * When set to true, ignore whether the LSAs were received from the network
3484 * or not. This parameter should be set to true when checking for topology
3485 * changes as part of the Graceful Restart helper neighbor procedures.
3486 *
3487 * Returns:
3488 * true if the LSAs are different, false otherwise.
3489 */
3490int ospf_lsa_different(struct ospf_lsa *l1, struct ospf_lsa *l2,
3491 bool ignore_rcvd_flag)
718e3744 3492{
d62a17ae 3493 char *p1, *p2;
3494 assert(l1);
3495 assert(l2);
3496 assert(l1->data);
3497 assert(l2->data);
718e3744 3498
d62a17ae 3499 if (l1->data->options != l2->data->options)
3500 return 1;
718e3744 3501
d62a17ae 3502 if (IS_LSA_MAXAGE(l1) && !IS_LSA_MAXAGE(l2))
3503 return 1;
718e3744 3504
d62a17ae 3505 if (IS_LSA_MAXAGE(l2) && !IS_LSA_MAXAGE(l1))
3506 return 1;
718e3744 3507
8db278b5 3508 if (l1->size != l2->size)
d62a17ae 3509 return 1;
718e3744 3510
8db278b5 3511 if (l1->size == 0)
d62a17ae 3512 return 1;
718e3744 3513
1bb2674c
RW
3514 if (!ignore_rcvd_flag
3515 && CHECK_FLAG((l1->flags ^ l2->flags), OSPF_LSA_RECEIVED))
d62a17ae 3516 return 1; /* May be a stale LSA in the LSBD */
5996e0df 3517
15c4dd82
LB
3518 if (l1->size == OSPF_LSA_HEADER_SIZE)
3519 return 0; /* nothing to compare */
718e3744 3520
d62a17ae 3521 p1 = (char *)l1->data;
3522 p2 = (char *)l2->data;
718e3744 3523
d62a17ae 3524 if (memcmp(p1 + OSPF_LSA_HEADER_SIZE, p2 + OSPF_LSA_HEADER_SIZE,
8db278b5 3525 l1->size - OSPF_LSA_HEADER_SIZE)
d62a17ae 3526 != 0)
3527 return 1;
718e3744 3528
d62a17ae 3529 return 0;
718e3744 3530}
3531
d62a17ae 3532int ospf_lsa_flush_schedule(struct ospf *ospf, struct ospf_lsa *lsa)
3533{
3534 if (lsa == NULL || !IS_LSA_SELF(lsa))
3535 return 0;
3536
3537 if (IS_DEBUG_OSPF_EVENT)
3538 zlog_debug(
96b663a3
MS
3539 "LSA[Type%d:%pI4]: Schedule self-originated LSA to FLUSH",
3540 lsa->data->type, &lsa->data->id);
d62a17ae 3541
3542 /* Force given lsa's age to MaxAge. */
3543 lsa->data->ls_age = htons(OSPF_LSA_MAXAGE);
3544
3545 switch (lsa->data->type) {
3546 /* Opaque wants to be notified of flushes */
3547 case OSPF_OPAQUE_LINK_LSA:
3548 case OSPF_OPAQUE_AREA_LSA:
3549 case OSPF_OPAQUE_AS_LSA:
3550 ospf_opaque_lsa_refresh(lsa);
3551 break;
3552 default:
3553 ospf_refresher_unregister_lsa(ospf, lsa);
3554 ospf_lsa_flush(ospf, lsa);
3555 break;
3556 }
3557
3558 return 0;
3559}
3560
3561void ospf_flush_self_originated_lsas_now(struct ospf *ospf)
3562{
3563 struct listnode *node, *nnode;
3564 struct listnode *node2, *nnode2;
3565 struct ospf_area *area;
3566 struct ospf_interface *oi;
3567 struct ospf_lsa *lsa;
3568 struct route_node *rn;
ca5997cd 3569 struct ospf_if_params *oip;
d62a17ae 3570 int need_to_flush_ase = 0;
3571
046460a1
CS
3572 ospf->inst_shutdown = 1;
3573
d62a17ae 3574 for (ALL_LIST_ELEMENTS(ospf->areas, node, nnode, area)) {
3575 if ((lsa = area->router_lsa_self) != NULL) {
3576 if (IS_DEBUG_OSPF_EVENT)
3577 zlog_debug(
96b663a3 3578 "LSA[Type%d:%pI4]: Schedule self-originated LSA to FLUSH",
d62a17ae 3579 lsa->data->type,
96b663a3 3580 &lsa->data->id);
d62a17ae 3581
3582 ospf_refresher_unregister_lsa(ospf, lsa);
3583 ospf_lsa_flush_area(lsa, area);
3584 ospf_lsa_unlock(&area->router_lsa_self);
3585 area->router_lsa_self = NULL;
3586 }
3587
3588 for (ALL_LIST_ELEMENTS(area->oiflist, node2, nnode2, oi)) {
3589 if ((lsa = oi->network_lsa_self) != NULL
3590 && oi->state == ISM_DR && oi->full_nbrs > 0) {
3591 if (IS_DEBUG_OSPF_EVENT)
3592 zlog_debug(
96b663a3 3593 "LSA[Type%d:%pI4]: Schedule self-originated LSA to FLUSH",
d62a17ae 3594 lsa->data->type,
96b663a3 3595 &lsa->data->id);
d62a17ae 3596
3597 ospf_refresher_unregister_lsa(
3598 ospf, oi->network_lsa_self);
3599 ospf_lsa_flush_area(oi->network_lsa_self, area);
3600 ospf_lsa_unlock(&oi->network_lsa_self);
3601 oi->network_lsa_self = NULL;
ca5997cd
MR
3602
3603 oip = ospf_lookup_if_params(
3604 oi->ifp, oi->address->u.prefix4);
3605 if (oip)
3606 oip->network_lsa_seqnum = htonl(
3607 OSPF_INVALID_SEQUENCE_NUMBER);
d62a17ae 3608 }
3609
3610 if (oi->type != OSPF_IFTYPE_VIRTUALLINK
3611 && area->external_routing == OSPF_AREA_DEFAULT)
3612 need_to_flush_ase = 1;
3613 }
3614
996c9314 3615 LSDB_LOOP (SUMMARY_LSDB(area), rn, lsa)
044506e7 3616 ospf_lsa_flush_schedule(ospf, lsa);
996c9314 3617 LSDB_LOOP (ASBR_SUMMARY_LSDB(area), rn, lsa)
044506e7 3618 ospf_lsa_flush_schedule(ospf, lsa);
996c9314 3619 LSDB_LOOP (OPAQUE_LINK_LSDB(area), rn, lsa)
044506e7 3620 ospf_lsa_flush_schedule(ospf, lsa);
996c9314 3621 LSDB_LOOP (OPAQUE_AREA_LSDB(area), rn, lsa)
044506e7 3622 ospf_lsa_flush_schedule(ospf, lsa);
d62a17ae 3623 }
3624
3625 if (need_to_flush_ase) {
996c9314 3626 LSDB_LOOP (EXTERNAL_LSDB(ospf), rn, lsa)
044506e7 3627 ospf_lsa_flush_schedule(ospf, lsa);
996c9314 3628 LSDB_LOOP (OPAQUE_AS_LSDB(ospf), rn, lsa)
044506e7 3629 ospf_lsa_flush_schedule(ospf, lsa);
d62a17ae 3630 }
3631
3632 /*
3633 * Make sure that the MaxAge LSA remover is executed immediately,
3634 * without conflicting to other threads.
3635 */
3636 if (ospf->t_maxage != NULL) {
cccd44f3 3637 THREAD_OFF(ospf->t_maxage);
d62a17ae 3638 thread_execute(master, ospf_maxage_lsa_remover, ospf, 0);
3639 }
3640
3641 return;
718e3744 3642}
718e3744 3643
3644/* If there is self-originated LSA, then return 1, otherwise return 0. */
3645/* An interface-independent version of ospf_lsa_is_self_originated */
d62a17ae 3646int ospf_lsa_is_self_originated(struct ospf *ospf, struct ospf_lsa *lsa)
3647{
3648 struct listnode *node;
3649 struct ospf_interface *oi;
3650
3651 /* This LSA is already checked. */
3652 if (CHECK_FLAG(lsa->flags, OSPF_LSA_SELF_CHECKED))
3653 return IS_LSA_SELF(lsa);
3654
3655 /* Make sure LSA is self-checked. */
3656 SET_FLAG(lsa->flags, OSPF_LSA_SELF_CHECKED);
3657
3658 /* AdvRouter and Router ID is the same. */
3659 if (IPV4_ADDR_SAME(&lsa->data->adv_router, &ospf->router_id))
3660 SET_FLAG(lsa->flags, OSPF_LSA_SELF);
3661
3662 /* LSA is router-LSA. */
3663 else if (lsa->data->type == OSPF_ROUTER_LSA
3664 && IPV4_ADDR_SAME(&lsa->data->id, &ospf->router_id))
3665 SET_FLAG(lsa->flags, OSPF_LSA_SELF);
3666
3667 /* LSA is network-LSA. Compare Link ID with all interfaces. */
3668 else if (lsa->data->type == OSPF_NETWORK_LSA)
3669 for (ALL_LIST_ELEMENTS_RO(ospf->oiflist, node, oi)) {
3670 /* Ignore virtual link. */
3671 if (oi->type != OSPF_IFTYPE_VIRTUALLINK)
3672 if (oi->address->family == AF_INET)
3673 if (IPV4_ADDR_SAME(
3674 &lsa->data->id,
3675 &oi->address->u.prefix4)) {
3676 /* to make it easier later */
3677 SET_FLAG(lsa->flags,
3678 OSPF_LSA_SELF);
3679 return IS_LSA_SELF(lsa);
3680 }
3681 }
3682
3683 return IS_LSA_SELF(lsa);
718e3744 3684}
3685
3686/* Get unique Link State ID. */
a8c22275 3687enum lsid_status ospf_lsa_unique_id(struct ospf *ospf, struct ospf_lsdb *lsdb,
3688 uint8_t type, struct prefix_ipv4 *p,
3689 struct in_addr *id)
d62a17ae 3690{
3691 struct ospf_lsa *lsa;
a8c22275 3692 struct in_addr mask;
d62a17ae 3693
a8c22275 3694 *id = p->prefix;
d62a17ae 3695
3696 /* Check existence of LSA instance. */
a8c22275 3697 lsa = ospf_lsdb_lookup_by_id(lsdb, type, *id, ospf->router_id);
d62a17ae 3698 if (lsa) {
3699 struct as_external_lsa *al =
3700 (struct as_external_lsa *)lsa->data;
a8c22275 3701 /* Ref rfc2328,Appendex E.1
3702 * If router already originated the external lsa with lsid
3703 * as the current prefix, and the masklens are same then
3704 * terminate the LSID algorithem.
3705 */
d62a17ae 3706 if (ip_masklen(al->mask) == p->prefixlen) {
3707 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
3708 zlog_debug(
a8c22275 3709 "%s: Can't get Link State ID for %pFX",
3710 __func__, p);
d62a17ae 3711 /* id.s_addr = 0; */
a8c22275 3712 id->s_addr = 0xffffffff;
3713 return LSID_NOT_AVAILABLE;
3714 } else if (ip_masklen(al->mask) < p->prefixlen) {
3715 /* Ref rfc2328,Appendex E.2
3716 * the current prefix masklen is greater than the
3717 * existing LSA, then generate the Link state ID,
3718 * by setting all host bits in prefix addressa and
3719 * originate.
3720 *
3721 * Eg: 1st Route : 10.0.0.0/16 - LSID:10.0.0.0
3722 * 2nd Route : 10.0.0.0/24 - LSID:10.0.0.255
3723 */
d62a17ae 3724 masklen2ip(p->prefixlen, &mask);
3725
a8c22275 3726 id->s_addr = p->prefix.s_addr | (~mask.s_addr);
3727 lsa = ospf_lsdb_lookup_by_id(ospf->lsdb, type, *id,
d62a17ae 3728 ospf->router_id);
3729 if (lsa) {
3730 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
3731 zlog_debug(
a8c22275 3732 "%s: Can't get Link State ID for %pFX",
3733 __func__, p);
3734 id->s_addr = 0xffffffff;
3735 return LSID_NOT_AVAILABLE;
3736 }
3737 } else {
3738 /* Ref rfc2328,Appendex E.3
3739 * the current prefix masklen is lesser than the
3740 * existing LSA,then the originated LSA has to be
3741 * refreshed by modifying masklen, cost and tag.
3742 * Originate the old route info with new LSID by
3743 * setting the host bits in prefix address.
3744 *
3745 * Eg: 1st Route : 10.0.0.0/24 - LSID:10.0.0.0
3746 * 2nd Route : 10.0.0.0/16 - ?
3747 * Since 2nd route mask len is less than firstone
3748 * LSID has to be changed.
3749 * 1st route LSID:10.0.0.255
3750 * 2nd route LSID:10.0.0.0
3751 */
3752 id->s_addr = lsa->data->id.s_addr | (~al->mask.s_addr);
3753 lsa = ospf_lsdb_lookup_by_id(ospf->lsdb, type, *id,
3754 ospf->router_id);
3755 if (lsa && (ip_masklen(al->mask) != IPV4_MAX_BITLEN)) {
3756 if (IS_DEBUG_OSPF(lsa, LSA_GENERATE))
3757 zlog_debug(
3758 "%s: Can't get Link State ID for %pFX",
3759 __func__, p);
3760 id->s_addr = 0xffffffff;
3761 return LSID_NOT_AVAILABLE;
d62a17ae 3762 }
a8c22275 3763 return LSID_CHANGE;
d62a17ae 3764 }
3765 }
3766
a8c22275 3767 return LSID_AVAILABLE;
718e3744 3768}
3769
6b0655a2 3770
70461d79
PJ
3771#define LSA_ACTION_FLOOD_AREA 1
3772#define LSA_ACTION_FLUSH_AREA 2
718e3744 3773
d62a17ae 3774struct lsa_action {
d7c0a89a 3775 uint8_t action;
d62a17ae 3776 struct ospf_area *area;
3777 struct ospf_lsa *lsa;
718e3744 3778};
3779
cc9f21da 3780static void ospf_lsa_action(struct thread *t)
718e3744 3781{
d62a17ae 3782 struct lsa_action *data;
718e3744 3783
d62a17ae 3784 data = THREAD_ARG(t);
718e3744 3785
d62a17ae 3786 if (IS_DEBUG_OSPF(lsa, LSA) == OSPF_DEBUG_LSA)
3787 zlog_debug("LSA[Action]: Performing scheduled LSA action: %d",
3788 data->action);
718e3744 3789
d62a17ae 3790 switch (data->action) {
3791 case LSA_ACTION_FLOOD_AREA:
3792 ospf_flood_through_area(data->area, NULL, data->lsa);
3793 break;
3794 case LSA_ACTION_FLUSH_AREA:
3795 ospf_lsa_flush_area(data->lsa, data->area);
3796 break;
3797 }
718e3744 3798
d62a17ae 3799 ospf_lsa_unlock(&data->lsa); /* Message */
3800 XFREE(MTYPE_OSPF_MESSAGE, data);
718e3744 3801}
3802
d62a17ae 3803void ospf_schedule_lsa_flood_area(struct ospf_area *area, struct ospf_lsa *lsa)
718e3744 3804{
d62a17ae 3805 struct lsa_action *data;
718e3744 3806
d62a17ae 3807 data = XCALLOC(MTYPE_OSPF_MESSAGE, sizeof(struct lsa_action));
3808 data->action = LSA_ACTION_FLOOD_AREA;
3809 data->area = area;
3810 data->lsa = ospf_lsa_lock(lsa); /* Message / Flood area */
718e3744 3811
d62a17ae 3812 thread_add_event(master, ospf_lsa_action, data, 0, NULL);
718e3744 3813}
3814
d62a17ae 3815void ospf_schedule_lsa_flush_area(struct ospf_area *area, struct ospf_lsa *lsa)
718e3744 3816{
d62a17ae 3817 struct lsa_action *data;
718e3744 3818
d62a17ae 3819 data = XCALLOC(MTYPE_OSPF_MESSAGE, sizeof(struct lsa_action));
3820 data->action = LSA_ACTION_FLUSH_AREA;
3821 data->area = area;
3822 data->lsa = ospf_lsa_lock(lsa); /* Message / Flush area */
718e3744 3823
d62a17ae 3824 thread_add_event(master, ospf_lsa_action, data, 0, NULL);
718e3744 3825}
3826
6b0655a2 3827
718e3744 3828/* LSA Refreshment functions. */
d62a17ae 3829struct ospf_lsa *ospf_lsa_refresh(struct ospf *ospf, struct ospf_lsa *lsa)
3830{
3831 struct external_info *ei;
960417cf 3832 struct ospf_external_aggr_rt *aggr;
d62a17ae 3833 struct ospf_lsa *new = NULL;
960417cf 3834 struct as_external_lsa *al;
3835 struct prefix_ipv4 p;
3836
405e1c84
DA
3837 assert(CHECK_FLAG(lsa->flags, OSPF_LSA_SELF));
3838 assert(IS_LSA_SELF(lsa));
d62a17ae 3839 assert(lsa->lock > 0);
3840
3841 switch (lsa->data->type) {
3842 /* Router and Network LSAs are processed differently. */
3843 case OSPF_ROUTER_LSA:
3844 new = ospf_router_lsa_refresh(lsa);
3845 break;
3846 case OSPF_NETWORK_LSA:
3847 new = ospf_network_lsa_refresh(lsa);
3848 break;
3849 case OSPF_SUMMARY_LSA:
3850 new = ospf_summary_lsa_refresh(ospf, lsa);
3851 break;
3852 case OSPF_ASBR_SUMMARY_LSA:
3853 new = ospf_summary_asbr_lsa_refresh(ospf, lsa);
3854 break;
3855 case OSPF_AS_EXTERNAL_LSA:
3856 /* Translated from NSSA Type-5s are refreshed when
3857 * from refresh of Type-7 - do not refresh these directly.
3858 */
960417cf 3859
3860 al = (struct as_external_lsa *)lsa->data;
3861 p.family = AF_INET;
3862 p.prefixlen = ip_masklen(al->mask);
3863 p.prefix = lsa->data->id;
3864
d62a17ae 3865 if (CHECK_FLAG(lsa->flags, OSPF_LSA_LOCAL_XLT))
3866 break;
b5a8894d 3867 ei = ospf_external_info_check(ospf, lsa);
d62a17ae 3868 if (ei)
63f0e941 3869 new = ospf_external_lsa_refresh(
3870 ospf, lsa, ei, LSA_REFRESH_FORCE, false);
960417cf 3871 else {
3872 aggr = (struct ospf_external_aggr_rt *)
3873 ospf_extrenal_aggregator_lookup(ospf, &p);
3874 if (aggr) {
3875 struct external_info ei_aggr;
3876
6006b807 3877 memset(&ei_aggr, 0, sizeof(ei_aggr));
960417cf 3878 ei_aggr.p = aggr->p;
3879 ei_aggr.tag = aggr->tag;
3880 ei_aggr.instance = ospf->instance;
3881 ei_aggr.route_map_set.metric = -1;
3882 ei_aggr.route_map_set.metric_type = -1;
3883
3884 ospf_external_lsa_refresh(ospf, lsa, &ei_aggr,
3885 LSA_REFRESH_FORCE, true);
d2e84005
MR
3886 SET_FLAG(aggr->flags,
3887 OSPF_EXTERNAL_AGGRT_ORIGINATED);
960417cf 3888 } else
3889 ospf_lsa_flush_as(ospf, lsa);
3890 }
d62a17ae 3891 break;
3892 case OSPF_OPAQUE_LINK_LSA:
3893 case OSPF_OPAQUE_AREA_LSA:
3894 case OSPF_OPAQUE_AS_LSA:
3895 new = ospf_opaque_lsa_refresh(lsa);
3896 break;
3897 default:
3898 break;
3899 }
3900 return new;
718e3744 3901}
3902
d62a17ae 3903void ospf_refresher_register_lsa(struct ospf *ospf, struct ospf_lsa *lsa)
3904{
d7c0a89a 3905 uint16_t index, current_index;
d62a17ae 3906
3907 assert(lsa->lock > 0);
405e1c84 3908 assert(IS_LSA_SELF(lsa));
d62a17ae 3909
3910 if (lsa->refresh_list < 0) {
3911 int delay;
3912 int min_delay =
b345a3d9
MN
3913 ospf->lsa_refresh_timer - (2 * OSPF_LS_REFRESH_JITTER);
3914 int max_delay =
3915 ospf->lsa_refresh_timer - OSPF_LS_REFRESH_JITTER;
d62a17ae 3916
3917 /* We want to refresh the LSA within OSPF_LS_REFRESH_TIME which
3918 * is
3919 * 1800s. Use jitter so that we send the LSA sometime between
3920 * 1680s
3921 * and 1740s.
3922 */
5920b3eb
RZ
3923 delay = (frr_weak_random() % (max_delay - min_delay))
3924 + min_delay;
d62a17ae 3925
3926 current_index = ospf->lsa_refresh_queue.index
3927 + (monotime(NULL) - ospf->lsa_refresher_started)
3928 / OSPF_LSA_REFRESHER_GRANULARITY;
3929
3930 index = (current_index + delay / OSPF_LSA_REFRESHER_GRANULARITY)
3931 % (OSPF_LSA_REFRESHER_SLOTS);
3932
3933 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH))
3934 zlog_debug(
96b663a3
MS
3935 "LSA[Refresh:Type%d:%pI4]: age %d, added to index %d",
3936 lsa->data->type, &lsa->data->id,
d62a17ae 3937 LS_AGE(lsa), index);
3938
3939 if (!ospf->lsa_refresh_queue.qs[index])
3940 ospf->lsa_refresh_queue.qs[index] = list_new();
3941
3942 listnode_add(ospf->lsa_refresh_queue.qs[index],
3943 ospf_lsa_lock(lsa)); /* lsa_refresh_queue */
3944 lsa->refresh_list = index;
3945
3946 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH))
3947 zlog_debug(
e6f3b262 3948 "LSA[Refresh:Type%d:%pI4]: %s: setting refresh_list on lsa %p (slot %d)",
3949 lsa->data->type, &lsa->data->id, __func__,
3950 (void *)lsa, index);
d62a17ae 3951 }
3952}
3953
3954void ospf_refresher_unregister_lsa(struct ospf *ospf, struct ospf_lsa *lsa)
3955{
3956 assert(lsa->lock > 0);
405e1c84 3957 assert(IS_LSA_SELF(lsa));
d62a17ae 3958 if (lsa->refresh_list >= 0) {
3959 struct list *refresh_list =
3960 ospf->lsa_refresh_queue.qs[lsa->refresh_list];
3961 listnode_delete(refresh_list, lsa);
3962 if (!listcount(refresh_list)) {
6a154c88 3963 list_delete(&refresh_list);
d62a17ae 3964 ospf->lsa_refresh_queue.qs[lsa->refresh_list] = NULL;
3965 }
d62a17ae 3966 lsa->refresh_list = -1;
a61b32f0 3967 ospf_lsa_unlock(&lsa); /* lsa_refresh_queue */
d62a17ae 3968 }
3969}
3970
cc9f21da 3971void ospf_lsa_refresh_walker(struct thread *t)
d62a17ae 3972{
3973 struct list *refresh_list;
3974 struct listnode *node, *nnode;
3975 struct ospf *ospf = THREAD_ARG(t);
3976 struct ospf_lsa *lsa;
3977 int i;
3978 struct list *lsa_to_refresh = list_new();
3979
3980 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH))
e6f3b262 3981 zlog_debug("LSA[Refresh]: %s: start", __func__);
d62a17ae 3982
3983
3984 i = ospf->lsa_refresh_queue.index;
3985
3986 /* Note: if clock has jumped backwards, then time change could be
3987 negative,
3988 so we are careful to cast the expression to unsigned before taking
3989 modulus. */
3990 ospf->lsa_refresh_queue.index =
3991 ((unsigned long)(ospf->lsa_refresh_queue.index
3992 + (monotime(NULL)
3993 - ospf->lsa_refresher_started)
3994 / OSPF_LSA_REFRESHER_GRANULARITY))
3995 % OSPF_LSA_REFRESHER_SLOTS;
3996
3997 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH))
e6f3b262 3998 zlog_debug("LSA[Refresh]: %s: next index %d", __func__,
3999 ospf->lsa_refresh_queue.index);
d62a17ae 4000
4001 for (; i != ospf->lsa_refresh_queue.index;
4002 i = (i + 1) % OSPF_LSA_REFRESHER_SLOTS) {
4003 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH))
e6f3b262 4004 zlog_debug("LSA[Refresh]: %s: refresh index %d",
4005 __func__, i);
d62a17ae 4006
4007 refresh_list = ospf->lsa_refresh_queue.qs[i];
4008
4009 assert(i >= 0);
4010
4011 ospf->lsa_refresh_queue.qs[i] = NULL;
4012
4013 if (refresh_list) {
4014 for (ALL_LIST_ELEMENTS(refresh_list, node, nnode,
4015 lsa)) {
4016 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH))
4017 zlog_debug(
e6f3b262 4018 "LSA[Refresh:Type%d:%pI4]: %s: refresh lsa %p (slot %d)",
4019 lsa->data->type, &lsa->data->id,
4020 __func__, (void *)lsa, i);
d62a17ae 4021
4022 assert(lsa->lock > 0);
4023 list_delete_node(refresh_list, node);
4024 lsa->refresh_list = -1;
4025 listnode_add(lsa_to_refresh, lsa);
4026 }
6a154c88 4027 list_delete(&refresh_list);
d62a17ae 4028 }
4029 }
4030
4031 ospf->t_lsa_refresher = NULL;
4032 thread_add_timer(master, ospf_lsa_refresh_walker, ospf,
4033 ospf->lsa_refresh_interval, &ospf->t_lsa_refresher);
4034 ospf->lsa_refresher_started = monotime(NULL);
4035
4036 for (ALL_LIST_ELEMENTS(lsa_to_refresh, node, nnode, lsa)) {
4037 ospf_lsa_refresh(ospf, lsa);
4038 assert(lsa->lock > 0);
4039 ospf_lsa_unlock(
4040 &lsa); /* lsa_refresh_queue & temp for lsa_to_refresh*/
4041 }
4042
6a154c88 4043 list_delete(&lsa_to_refresh);
d62a17ae 4044
4045 if (IS_DEBUG_OSPF(lsa, LSA_REFRESH))
e6f3b262 4046 zlog_debug("LSA[Refresh]: %s: end", __func__);
d62a17ae 4047}
44445dee
S
4048
4049/* Flush the LSAs for the specific area */
4050void ospf_flush_lsa_from_area(struct ospf *ospf, struct in_addr area_id,
4051 int type)
4052{
4053 struct ospf_area *area;
4054 struct route_node *rn;
4055 struct ospf_lsa *lsa;
4056
4057 area = ospf_area_get(ospf, area_id);
4058
4059 switch (type) {
4060 case OSPF_AS_EXTERNAL_LSA:
4061 if ((area->external_routing == OSPF_AREA_NSSA) ||
4062 (area->external_routing == OSPF_AREA_STUB)) {
4063 LSDB_LOOP (EXTERNAL_LSDB(ospf), rn, lsa)
4064 if (IS_LSA_SELF(lsa) &&
4065 !(CHECK_FLAG(lsa->flags,
4066 OSPF_LSA_LOCAL_XLT)))
4067 ospf_lsa_flush_area(lsa, area);
4068 }
4069 break;
4070 case OSPF_AS_NSSA_LSA:
4071 LSDB_LOOP (NSSA_LSDB(area), rn, lsa)
4072 if (IS_LSA_SELF(lsa))
4073 ospf_lsa_flush_area(lsa, area);
4074 break;
4075 default:
4076 break;
4077 }
4078}