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