]> git.proxmox.com Git - mirror_frr.git/blame - bgpd/bgp_packet.c
Merge pull request #7809 from donaldsharp/m_coverity
[mirror_frr.git] / bgpd / bgp_packet.c
CommitLineData
718e3744 1/* BGP packet management routine.
56257a44
QY
2 * Contains utility functions for constructing and consuming BGP messages.
3 * Copyright (C) 2017 Cumulus Networks
896014f4
DL
4 * Copyright (C) 1999 Kunihiro Ishiguro
5 *
6 * This file is part of GNU Zebra.
7 *
8 * GNU Zebra is free software; you can redistribute it and/or modify it
9 * under the terms of the GNU General Public License as published by the
10 * Free Software Foundation; either version 2, or (at your option) any
11 * later version.
12 *
13 * GNU Zebra is distributed in the hope that it will be useful, but
14 * WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License along
19 * with this program; see the file COPYING; if not, write to the Free Software
20 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
21 */
718e3744 22
23#include <zebra.h>
d3ecc69e 24#include <sys/time.h>
718e3744 25
26#include "thread.h"
27#include "stream.h"
28#include "network.h"
29#include "prefix.h"
30#include "command.h"
31#include "log.h"
32#include "memory.h"
d62a17ae 33#include "sockunion.h" /* for inet_ntop () */
baa376fc 34#include "sockopt.h"
718e3744 35#include "linklist.h"
36#include "plist.h"
3f9c7369 37#include "queue.h"
039f3a34 38#include "filter.h"
02705213 39#include "lib_errors.h"
718e3744 40
41#include "bgpd/bgpd.h"
42#include "bgpd/bgp_table.h"
43#include "bgpd/bgp_dump.h"
6c29258c 44#include "bgpd/bgp_bmp.h"
718e3744 45#include "bgpd/bgp_attr.h"
46#include "bgpd/bgp_debug.h"
14454c9f 47#include "bgpd/bgp_errors.h"
718e3744 48#include "bgpd/bgp_fsm.h"
49#include "bgpd/bgp_route.h"
50#include "bgpd/bgp_packet.h"
51#include "bgpd/bgp_open.h"
52#include "bgpd/bgp_aspath.h"
53#include "bgpd/bgp_community.h"
54#include "bgpd/bgp_ecommunity.h"
57d187bc 55#include "bgpd/bgp_lcommunity.h"
718e3744 56#include "bgpd/bgp_network.h"
57#include "bgpd/bgp_mplsvpn.h"
7ef5a232 58#include "bgpd/bgp_evpn.h"
718e3744 59#include "bgpd/bgp_advertise.h"
93406d87 60#include "bgpd/bgp_vty.h"
3f9c7369 61#include "bgpd/bgp_updgrp.h"
cd1964ff 62#include "bgpd/bgp_label.h"
56257a44 63#include "bgpd/bgp_io.h"
934af458 64#include "bgpd/bgp_keepalives.h"
7c40bf39 65#include "bgpd/bgp_flowspec.h"
d9a03c57 66#include "bgpd/bgp_trace.h"
718e3744 67
584470fb
DL
68DEFINE_HOOK(bgp_packet_dump,
69 (struct peer *peer, uint8_t type, bgp_size_t size,
70 struct stream *s),
71 (peer, type, size, s))
72
6fd04594
DL
73DEFINE_HOOK(bgp_packet_send,
74 (struct peer *peer, uint8_t type, bgp_size_t size,
75 struct stream *s),
76 (peer, type, size, s))
77
d8151687
QY
78/**
79 * Sets marker and type fields for a BGP message.
80 *
81 * @param s the stream containing the packet
82 * @param type the packet type
83 * @return the size of the stream
84 */
d7c0a89a 85int bgp_packet_set_marker(struct stream *s, uint8_t type)
718e3744 86{
d62a17ae 87 int i;
718e3744 88
d62a17ae 89 /* Fill in marker. */
90 for (i = 0; i < BGP_MARKER_SIZE; i++)
91 stream_putc(s, 0xff);
718e3744 92
d62a17ae 93 /* Dummy total length. This field is should be filled in later on. */
94 stream_putw(s, 0);
718e3744 95
d62a17ae 96 /* BGP packet type. */
97 stream_putc(s, type);
718e3744 98
d62a17ae 99 /* Return current stream size. */
100 return stream_get_endp(s);
718e3744 101}
102
d8151687
QY
103/**
104 * Sets size field for a BGP message.
105 *
106 * Size field is set to the size of the stream passed.
107 *
108 * @param s the stream containing the packet
109 * @return the size of the stream
110 */
d62a17ae 111int bgp_packet_set_size(struct stream *s)
718e3744 112{
d62a17ae 113 int cp;
718e3744 114
d62a17ae 115 /* Preserve current pointer. */
116 cp = stream_get_endp(s);
117 stream_putw_at(s, BGP_MARKER_SIZE, cp);
718e3744 118
d62a17ae 119 return cp;
718e3744 120}
121
d3ecc69e
QY
122/*
123 * Push a packet onto the beginning of the peer's output queue.
124 * This function acquires the peer's write mutex before proceeding.
125 */
126static void bgp_packet_add(struct peer *peer, struct stream *s)
127{
00dffa8c
DL
128 frr_with_mutex(&peer->io_mtx) {
129 stream_fifo_push(peer->obuf, s);
130 }
718e3744 131}
132
d62a17ae 133static struct stream *bgp_update_packet_eor(struct peer *peer, afi_t afi,
134 safi_t safi)
93406d87 135{
d62a17ae 136 struct stream *s;
137 iana_afi_t pkt_afi;
5c525538 138 iana_safi_t pkt_safi;
d62a17ae 139
140 if (DISABLE_BGP_ANNOUNCE)
141 return NULL;
142
143 if (bgp_debug_neighbor_events(peer))
144 zlog_debug("send End-of-RIB for %s to %s",
5cb5f4d0 145 get_afi_safi_str(afi, safi, false), peer->host);
d62a17ae 146
147 s = stream_new(BGP_MAX_PACKET_SIZE);
148
149 /* Make BGP update packet. */
150 bgp_packet_set_marker(s, BGP_MSG_UPDATE);
151
152 /* Unfeasible Routes Length */
153 stream_putw(s, 0);
154
155 if (afi == AFI_IP && safi == SAFI_UNICAST) {
156 /* Total Path Attribute Length */
157 stream_putw(s, 0);
158 } else {
159 /* Convert AFI, SAFI to values for packet. */
160 bgp_map_afi_safi_int2iana(afi, safi, &pkt_afi, &pkt_safi);
161
162 /* Total Path Attribute Length */
163 stream_putw(s, 6);
164 stream_putc(s, BGP_ATTR_FLAG_OPTIONAL);
165 stream_putc(s, BGP_ATTR_MP_UNREACH_NLRI);
166 stream_putc(s, 3);
167 stream_putw(s, pkt_afi);
168 stream_putc(s, pkt_safi);
169 }
170
171 bgp_packet_set_size(s);
d62a17ae 172 return s;
718e3744 173}
174
d8151687
QY
175/* Called when there is a change in the EOR(implicit or explicit) status of a
176 * peer. Ends the update-delay if all expected peers are done with EORs. */
177void bgp_check_update_delay(struct bgp *bgp)
178{
179 struct listnode *node, *nnode;
180 struct peer *peer = NULL;
181
182 if (bgp_debug_neighbor_events(peer))
183 zlog_debug("Checking update delay, T: %d R: %d I:%d E: %d",
184 bgp->established, bgp->restarted_peers,
185 bgp->implicit_eors, bgp->explicit_eors);
186
187 if (bgp->established
188 <= bgp->restarted_peers + bgp->implicit_eors + bgp->explicit_eors) {
becedef6
QY
189 /*
190 * This is an extra sanity check to make sure we wait for all
191 * the eligible configured peers. This check is performed if
192 * establish wait timer is on, or establish wait option is not
193 * given with the update-delay command
194 */
d8151687
QY
195 if (bgp->t_establish_wait
196 || (bgp->v_establish_wait == bgp->v_update_delay))
197 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer)) {
198 if (CHECK_FLAG(peer->flags,
199 PEER_FLAG_CONFIG_NODE)
200 && !CHECK_FLAG(peer->flags,
201 PEER_FLAG_SHUTDOWN)
cb9196e7
DS
202 && !CHECK_FLAG(peer->bgp->flags,
203 BGP_FLAG_SHUTDOWN)
d8151687
QY
204 && !peer->update_delay_over) {
205 if (bgp_debug_neighbor_events(peer))
206 zlog_debug(
207 " Peer %s pending, continuing read-only mode",
208 peer->host);
209 return;
210 }
211 }
212
213 zlog_info(
214 "Update delay ended, restarted: %d, EORs implicit: %d, explicit: %d",
215 bgp->restarted_peers, bgp->implicit_eors,
216 bgp->explicit_eors);
217 bgp_update_delay_end(bgp);
218 }
219}
220
becedef6
QY
221/*
222 * Called if peer is known to have restarted. The restart-state bit in
223 * Graceful-Restart capability is used for that
224 */
d8151687
QY
225void bgp_update_restarted_peers(struct peer *peer)
226{
227 if (!bgp_update_delay_active(peer->bgp))
228 return; /* BGP update delay has ended */
229 if (peer->update_delay_over)
230 return; /* This peer has already been considered */
231
232 if (bgp_debug_neighbor_events(peer))
233 zlog_debug("Peer %s: Checking restarted", peer->host);
234
235 if (peer->status == Established) {
236 peer->update_delay_over = 1;
237 peer->bgp->restarted_peers++;
238 bgp_check_update_delay(peer->bgp);
239 }
240}
241
becedef6
QY
242/*
243 * Called as peer receives a keep-alive. Determines if this occurence can be
244 * taken as an implicit EOR for this peer.
245 * NOTE: The very first keep-alive after the Established state of a peer is
246 * considered implicit EOR for the update-delay purposes
247 */
d8151687
QY
248void bgp_update_implicit_eors(struct peer *peer)
249{
250 if (!bgp_update_delay_active(peer->bgp))
251 return; /* BGP update delay has ended */
252 if (peer->update_delay_over)
253 return; /* This peer has already been considered */
254
255 if (bgp_debug_neighbor_events(peer))
256 zlog_debug("Peer %s: Checking implicit EORs", peer->host);
257
258 if (peer->status == Established) {
259 peer->update_delay_over = 1;
260 peer->bgp->implicit_eors++;
261 bgp_check_update_delay(peer->bgp);
262 }
263}
264
becedef6
QY
265/*
266 * Should be called only when there is a change in the EOR_RECEIVED status
267 * for any afi/safi on a peer.
268 */
d8151687
QY
269static void bgp_update_explicit_eors(struct peer *peer)
270{
271 afi_t afi;
272 safi_t safi;
273
274 if (!bgp_update_delay_active(peer->bgp))
275 return; /* BGP update delay has ended */
276 if (peer->update_delay_over)
277 return; /* This peer has already been considered */
278
279 if (bgp_debug_neighbor_events(peer))
280 zlog_debug("Peer %s: Checking explicit EORs", peer->host);
281
f18ba3cd
DS
282 FOREACH_AFI_SAFI (afi, safi) {
283 if (peer->afc_nego[afi][safi]
284 && !CHECK_FLAG(peer->af_sflags[afi][safi],
285 PEER_STATUS_EOR_RECEIVED)) {
286 if (bgp_debug_neighbor_events(peer))
287 zlog_debug(
288 " afi %d safi %d didn't receive EOR",
289 afi, safi);
290 return;
d8151687 291 }
f18ba3cd 292 }
d8151687
QY
293
294 peer->update_delay_over = 1;
295 peer->bgp->explicit_eors++;
296 bgp_check_update_delay(peer->bgp);
297}
298
299/**
300 * Frontend for NLRI parsing, to fan-out to AFI/SAFI specific parsers.
301 *
302 * mp_withdraw, if set, is used to nullify attr structure on most of the
303 * calling safi function and for evpn, passed as parameter
304 */
305int bgp_nlri_parse(struct peer *peer, struct attr *attr,
306 struct bgp_nlri *packet, int mp_withdraw)
307{
308 switch (packet->safi) {
309 case SAFI_UNICAST:
310 case SAFI_MULTICAST:
311 return bgp_nlri_parse_ip(peer, mp_withdraw ? NULL : attr,
312 packet);
313 case SAFI_LABELED_UNICAST:
314 return bgp_nlri_parse_label(peer, mp_withdraw ? NULL : attr,
315 packet);
316 case SAFI_MPLS_VPN:
317 return bgp_nlri_parse_vpn(peer, mp_withdraw ? NULL : attr,
318 packet);
319 case SAFI_EVPN:
320 return bgp_nlri_parse_evpn(peer, attr, packet, mp_withdraw);
7c40bf39 321 case SAFI_FLOWSPEC:
322 return bgp_nlri_parse_flowspec(peer, attr, packet, mp_withdraw);
d8151687 323 }
513386b5 324 return BGP_NLRI_PARSE_ERROR;
d8151687
QY
325}
326
6ec98a2f
QY
327/*
328 * Checks a variety of conditions to determine whether the peer needs to be
329 * rescheduled for packet generation again, and does so if necessary.
330 *
331 * @param peer to check for rescheduling
332 */
af1e1dc6
QY
333static void bgp_write_proceed_actions(struct peer *peer)
334{
335 afi_t afi;
336 safi_t safi;
337 struct peer_af *paf;
338 struct bpacket *next_pkt;
339 struct update_subgroup *subgrp;
340
c58b0f46
QY
341 FOREACH_AFI_SAFI (afi, safi) {
342 paf = peer_af_find(peer, afi, safi);
343 if (!paf)
344 continue;
345 subgrp = paf->subgroup;
346 if (!subgrp)
347 continue;
348
349 next_pkt = paf->next_pkt_to_send;
350 if (next_pkt && next_pkt->buffer) {
351 BGP_TIMER_ON(peer->t_generate_updgrp_packets,
352 bgp_generate_updgrp_packets, 0);
353 return;
354 }
af1e1dc6 355
c58b0f46
QY
356 /* No packets readily available for AFI/SAFI, are there
357 * subgroup packets
358 * that need to be generated? */
359 if (bpacket_queue_is_full(SUBGRP_INST(subgrp),
360 SUBGRP_PKTQ(subgrp))
361 || subgroup_packets_to_build(subgrp)) {
362 BGP_TIMER_ON(peer->t_generate_updgrp_packets,
363 bgp_generate_updgrp_packets, 0);
364 return;
365 }
af1e1dc6 366
c58b0f46
QY
367 /* No packets to send, see if EOR is pending */
368 if (CHECK_FLAG(peer->cap, PEER_CAP_RESTART_RCV)) {
369 if (!subgrp->t_coalesce && peer->afc_nego[afi][safi]
370 && peer->synctime
371 && !CHECK_FLAG(peer->af_sflags[afi][safi],
372 PEER_STATUS_EOR_SEND)
373 && safi != SAFI_MPLS_VPN) {
af1e1dc6
QY
374 BGP_TIMER_ON(peer->t_generate_updgrp_packets,
375 bgp_generate_updgrp_packets, 0);
376 return;
377 }
af1e1dc6 378 }
c58b0f46 379 }
af1e1dc6
QY
380}
381
6ec98a2f
QY
382/*
383 * Generate advertisement information (withdraws, updates, EOR) from each
384 * update group a peer belongs to, encode this information into packets, and
385 * enqueue the packets onto the peer's output buffer.
56257a44
QY
386 */
387int bgp_generate_updgrp_packets(struct thread *thread)
718e3744 388{
56257a44 389 struct peer *peer = THREAD_ARG(thread);
56257a44
QY
390
391 struct stream *s;
d62a17ae 392 struct peer_af *paf;
393 struct bpacket *next_pkt;
d0ad6d8e
QY
394 uint32_t wpq;
395 uint32_t generated = 0;
d62a17ae 396 afi_t afi;
397 safi_t safi;
398
d0ad6d8e
QY
399 wpq = atomic_load_explicit(&peer->bgp->wpkt_quanta,
400 memory_order_relaxed);
401
d62a17ae 402 /*
403 * The code beyond this part deals with update packets, proceed only
404 * if peer is Established and updates are not on hold (as part of
f4d2dd84 405 * update-delay processing).
3f9c7369 406 */
d62a17ae 407 if (peer->status != Established)
56257a44 408 return 0;
d62a17ae 409
f4d2dd84
DS
410 if ((peer->bgp->main_peers_update_hold)
411 || bgp_update_delay_active(peer->bgp))
56257a44 412 return 0;
d62a17ae 413
b10b6d52
RW
414 if (peer->t_routeadv)
415 return 0;
416
56257a44
QY
417 do {
418 s = NULL;
c58b0f46
QY
419 FOREACH_AFI_SAFI (afi, safi) {
420 paf = peer_af_find(peer, afi, safi);
421 if (!paf || !PAF_SUBGRP(paf))
422 continue;
423 next_pkt = paf->next_pkt_to_send;
80bd61c4 424
c58b0f46
QY
425 /*
426 * Try to generate a packet for the peer if we are at
427 * the end of the list. Always try to push out
428 * WITHDRAWs first.
429 */
430 if (!next_pkt || !next_pkt->buffer) {
431 next_pkt = subgroup_withdraw_packet(
432 PAF_SUBGRP(paf));
433 if (!next_pkt || !next_pkt->buffer)
434 subgroup_update_packet(PAF_SUBGRP(paf));
435 next_pkt = paf->next_pkt_to_send;
436 }
80bd61c4 437
c58b0f46
QY
438 /*
439 * If we still don't have a packet to send to the peer,
440 * then try to find out out if we have to send eor or
441 * if not, skip to the next AFI, SAFI. Don't send the
442 * EOR prematurely; if the subgroup's coalesce timer is
443 * running, the adjacency-out structure is not created
444 * yet.
445 */
446 if (!next_pkt || !next_pkt->buffer) {
447 if (CHECK_FLAG(peer->cap,
36235319 448 PEER_CAP_RESTART_RCV)) {
c58b0f46 449 if (!(PAF_SUBGRP(paf))->t_coalesce
36235319
QY
450 && peer->afc_nego[afi][safi]
451 && peer->synctime
452 && !CHECK_FLAG(
453 peer->af_sflags[afi][safi],
454 PEER_STATUS_EOR_SEND)) {
d6e3c15b 455 /* If EOR is disabled,
456 * the message is not sent
457 */
36235319
QY
458 if (BGP_SEND_EOR(peer->bgp, afi,
459 safi)) {
d6e3c15b 460 SET_FLAG(
36235319
QY
461 peer->af_sflags
462 [afi]
463 [safi],
464 PEER_STATUS_EOR_SEND);
d6e3c15b 465
9e3b51a7 466 /* Update EOR
467 * send time
468 */
36235319
QY
469 peer->eor_stime[afi]
470 [safi] =
471 monotime(NULL);
9e3b51a7 472
d6e3c15b 473 BGP_UPDATE_EOR_PKT(
36235319
QY
474 peer, afi, safi,
475 s);
56257a44 476 }
80bd61c4 477 }
d62a17ae 478 }
c58b0f46
QY
479 continue;
480 }
9e3b51a7 481
482 /* Update packet send time */
483 peer->pkt_stime[afi][safi] = monotime(NULL);
484
c58b0f46
QY
485 /* Found a packet template to send, overwrite
486 * packet with appropriate attributes from peer
487 * and advance peer */
488 s = bpacket_reformat_for_peer(next_pkt, paf);
489 bgp_packet_add(peer, s);
c58b0f46
QY
490 bpacket_queue_advance_peer(paf);
491 }
d0ad6d8e 492 } while (s && (++generated < wpq));
80bd61c4 493
6ec98a2f
QY
494 if (generated)
495 bgp_writes_on(peer);
496
af1e1dc6
QY
497 bgp_write_proceed_actions(peer);
498
80bd61c4
QY
499 return 0;
500}
501
d3ecc69e
QY
502/*
503 * Creates a BGP Keepalive packet and appends it to the peer's output queue.
504 */
d62a17ae 505void bgp_keepalive_send(struct peer *peer)
718e3744 506{
d62a17ae 507 struct stream *s;
508
509 s = stream_new(BGP_MAX_PACKET_SIZE);
718e3744 510
d62a17ae 511 /* Make keepalive packet. */
512 bgp_packet_set_marker(s, BGP_MSG_KEEPALIVE);
718e3744 513
d62a17ae 514 /* Set packet size. */
515 (void)bgp_packet_set_size(s);
718e3744 516
d62a17ae 517 /* Dump packet if debug option is set. */
518 /* bgp_packet_dump (s); */
718e3744 519
d62a17ae 520 if (bgp_debug_keepalive(peer))
521 zlog_debug("%s sending KEEPALIVE", peer->host);
718e3744 522
d62a17ae 523 /* Add packet to the peer. */
524 bgp_packet_add(peer, s);
424ab01d
QY
525
526 bgp_writes_on(peer);
718e3744 527}
528
d3ecc69e
QY
529/*
530 * Creates a BGP Open packet and appends it to the peer's output queue.
531 * Sets capabilities as necessary.
532 */
d62a17ae 533void bgp_open_send(struct peer *peer)
718e3744 534{
d62a17ae 535 struct stream *s;
d7c0a89a 536 uint16_t send_holdtime;
d62a17ae 537 as_t local_as;
718e3744 538
b90a8e13 539 if (CHECK_FLAG(peer->flags, PEER_FLAG_TIMER))
d62a17ae 540 send_holdtime = peer->holdtime;
541 else
542 send_holdtime = peer->bgp->default_holdtime;
718e3744 543
d62a17ae 544 /* local-as Change */
545 if (peer->change_local_as)
546 local_as = peer->change_local_as;
547 else
548 local_as = peer->local_as;
718e3744 549
d62a17ae 550 s = stream_new(BGP_MAX_PACKET_SIZE);
718e3744 551
d62a17ae 552 /* Make open packet. */
553 bgp_packet_set_marker(s, BGP_MSG_OPEN);
718e3744 554
d62a17ae 555 /* Set open packet values. */
556 stream_putc(s, BGP_VERSION_4); /* BGP version */
d7c0a89a
QY
557 stream_putw(s, (local_as <= BGP_AS_MAX) ? (uint16_t)local_as
558 : BGP_AS_TRANS);
d62a17ae 559 stream_putw(s, send_holdtime); /* Hold Time */
560 stream_put_in_addr(s, &peer->local_id); /* BGP Identifier */
718e3744 561
d62a17ae 562 /* Set capability code. */
563 bgp_open_capability(s, peer);
718e3744 564
d62a17ae 565 /* Set BGP packet length. */
566 (void)bgp_packet_set_size(s);
718e3744 567
d62a17ae 568 if (bgp_debug_neighbor_events(peer))
569 zlog_debug(
23d0a753 570 "%s sending OPEN, version %d, my as %u, holdtime %d, id %pI4",
d62a17ae 571 peer->host, BGP_VERSION_4, local_as, send_holdtime,
23d0a753 572 &peer->local_id);
718e3744 573
d62a17ae 574 /* Dump packet if debug option is set. */
575 /* bgp_packet_dump (s); */
6fd04594 576 hook_call(bgp_packet_send, peer, BGP_MSG_OPEN, stream_get_endp(s), s);
718e3744 577
d62a17ae 578 /* Add packet to the peer. */
579 bgp_packet_add(peer, s);
424ab01d
QY
580
581 bgp_writes_on(peer);
582}
583
a127f33b
QY
584/*
585 * Writes NOTIFICATION message directly to a peer socket without waiting for
586 * the I/O thread.
587 *
588 * There must be exactly one stream on the peer->obuf FIFO, and the data within
589 * this stream must match the format of a BGP NOTIFICATION message.
590 * Transmission is best-effort.
591 *
592 * @requires peer->io_mtx
593 * @param peer
594 * @return 0
595 */
3dc339cd 596static void bgp_write_notify(struct peer *peer)
424ab01d
QY
597{
598 int ret, val;
d7c0a89a 599 uint8_t type;
424ab01d
QY
600 struct stream *s;
601
a127f33b
QY
602 /* There should be at least one packet. */
603 s = stream_fifo_pop(peer->obuf);
424ab01d 604
8ec586b0 605 if (!s)
3dc339cd 606 return;
8ec586b0
QY
607
608 assert(stream_get_endp(s) >= BGP_HEADER_SIZE);
609
424ab01d
QY
610 /* Stop collecting data within the socket */
611 sockopt_cork(peer->fd, 0);
612
becedef6
QY
613 /*
614 * socket is in nonblocking mode, if we can't deliver the NOTIFY, well,
615 * we only care about getting a clean shutdown at this point.
616 */
424ab01d
QY
617 ret = write(peer->fd, STREAM_DATA(s), stream_get_endp(s));
618
becedef6
QY
619 /*
620 * only connection reset/close gets counted as TCP_fatal_error, failure
621 * to write the entire NOTIFY doesn't get different FSM treatment
622 */
424ab01d 623 if (ret <= 0) {
3735936b 624 stream_free(s);
424ab01d 625 BGP_EVENT_ADD(peer, TCP_fatal_error);
3dc339cd 626 return;
424ab01d
QY
627 }
628
629 /* Disable Nagle, make NOTIFY packet go out right away */
630 val = 1;
631 (void)setsockopt(peer->fd, IPPROTO_TCP, TCP_NODELAY, (char *)&val,
632 sizeof(val));
633
634 /* Retrieve BGP packet type. */
635 stream_set_getp(s, BGP_MARKER_SIZE + 2);
636 type = stream_getc(s);
637
638 assert(type == BGP_MSG_NOTIFY);
639
640 /* Type should be notify. */
0112e9e0 641 atomic_fetch_add_explicit(&peer->notify_out, 1, memory_order_relaxed);
424ab01d
QY
642 peer->notify_out++;
643
644 /* Double start timer. */
645 peer->v_start *= 2;
646
647 /* Overflow check. */
648 if (peer->v_start >= (60 * 2))
649 peer->v_start = (60 * 2);
650
becedef6
QY
651 /*
652 * Handle Graceful Restart case where the state changes to
653 * Connect instead of Idle
654 */
424ab01d
QY
655 BGP_EVENT_ADD(peer, BGP_Stop);
656
3735936b 657 stream_free(s);
718e3744 658}
659
d3ecc69e
QY
660/*
661 * Creates a BGP Notify and appends it to the peer's output queue.
662 *
becedef6
QY
663 * This function attempts to write the packet from the thread it is called
664 * from, to ensure the packet gets out ASAP.
d3ecc69e 665 *
a127f33b
QY
666 * This function may be called from multiple threads. Since the function
667 * modifies I/O buffer(s) in the peer, these are locked for the duration of the
668 * call to prevent tampering from other threads.
669 *
670 * Delivery of the NOTIFICATION is attempted once and is best-effort. After
671 * return, the peer structure *must* be reset; no assumptions about session
672 * state are valid.
673 *
d3ecc69e
QY
674 * @param peer
675 * @param code BGP error code
676 * @param sub_code BGP error subcode
677 * @param data Data portion
678 * @param datalen length of data portion
679 */
d7c0a89a
QY
680void bgp_notify_send_with_data(struct peer *peer, uint8_t code,
681 uint8_t sub_code, uint8_t *data, size_t datalen)
718e3744 682{
d62a17ae 683 struct stream *s;
d62a17ae 684
a127f33b 685 /* Lock I/O mutex to prevent other threads from pushing packets */
00dffa8c 686 frr_mutex_lock_autounlock(&peer->io_mtx);
a127f33b
QY
687 /* ============================================== */
688
d62a17ae 689 /* Allocate new stream. */
690 s = stream_new(BGP_MAX_PACKET_SIZE);
691
d3ecc69e 692 /* Make notify packet. */
d62a17ae 693 bgp_packet_set_marker(s, BGP_MSG_NOTIFY);
694
695 /* Set notify packet values. */
696 stream_putc(s, code); /* BGP notify code */
697 stream_putc(s, sub_code); /* BGP notify sub_code */
698
699 /* If notify data is present. */
700 if (data)
701 stream_write(s, data, datalen);
702
703 /* Set BGP packet length. */
bd6b2706 704 bgp_packet_set_size(s);
d62a17ae 705
424ab01d 706 /* wipe output buffer */
a127f33b 707 stream_fifo_clean(peer->obuf);
d62a17ae 708
becedef6
QY
709 /*
710 * If possible, store last packet for debugging purposes. This check is
711 * in place because we are sometimes called with a doppelganger peer,
712 * who tends to have a plethora of fields nulled out.
713 */
1a1f4534 714 if (peer->curr) {
d8151687 715 size_t packetsize = stream_get_endp(peer->curr);
1a1f4534 716 assert(packetsize <= sizeof(peer->last_reset_cause));
d8151687
QY
717 memcpy(peer->last_reset_cause, peer->curr->data, packetsize);
718 peer->last_reset_cause_size = packetsize;
719 }
720
d62a17ae 721 /* For debug */
722 {
723 struct bgp_notify bgp_notify;
724 int first = 0;
725 int i;
726 char c[4];
727
728 bgp_notify.code = code;
729 bgp_notify.subcode = sub_code;
730 bgp_notify.data = NULL;
e0981960 731 bgp_notify.length = datalen;
d62a17ae 732 bgp_notify.raw_data = data;
733
734 peer->notify.code = bgp_notify.code;
735 peer->notify.subcode = bgp_notify.subcode;
736
e0981960 737 if (bgp_notify.length && data) {
d62a17ae 738 bgp_notify.data =
739 XMALLOC(MTYPE_TMP, bgp_notify.length * 3);
740 for (i = 0; i < bgp_notify.length; i++)
741 if (first) {
552d6491
QY
742 snprintf(c, sizeof(c), " %02x",
743 data[i]);
f009ff26 744
552d6491 745 strlcat(bgp_notify.data, c,
2ba1fe69 746 bgp_notify.length);
f009ff26 747
d62a17ae 748 } else {
749 first = 1;
552d6491 750 snprintf(c, sizeof(c), "%02x", data[i]);
f009ff26 751
552d6491 752 strlcpy(bgp_notify.data, c,
2ba1fe69 753 bgp_notify.length);
d62a17ae 754 }
755 }
756 bgp_notify_print(peer, &bgp_notify, "sending");
757
758 if (bgp_notify.data) {
759 XFREE(MTYPE_TMP, bgp_notify.data);
d62a17ae 760 bgp_notify.length = 0;
761 }
762 }
763
764 /* peer reset cause */
765 if (code == BGP_NOTIFY_CEASE) {
766 if (sub_code == BGP_NOTIFY_CEASE_ADMIN_RESET)
767 peer->last_reset = PEER_DOWN_USER_RESET;
768 else if (sub_code == BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN)
769 peer->last_reset = PEER_DOWN_USER_SHUTDOWN;
770 else
771 peer->last_reset = PEER_DOWN_NOTIFY_SEND;
772 } else
773 peer->last_reset = PEER_DOWN_NOTIFY_SEND;
774
d3ecc69e 775 /* Add packet to peer's output queue */
a127f33b 776 stream_fifo_push(peer->obuf, s);
424ab01d 777
5cce3f05 778 bgp_peer_gr_flags_update(peer);
36235319
QY
779 BGP_GR_ROUTER_DETECT_AND_SEND_CAPABILITY_TO_ZEBRA(peer->bgp,
780 peer->bgp->peer);
5cce3f05 781
424ab01d 782 bgp_write_notify(peer);
718e3744 783}
784
d3ecc69e
QY
785/*
786 * Creates a BGP Notify and appends it to the peer's output queue.
787 *
becedef6
QY
788 * This function attempts to write the packet from the thread it is called
789 * from, to ensure the packet gets out ASAP.
d3ecc69e
QY
790 *
791 * @param peer
792 * @param code BGP error code
793 * @param sub_code BGP error subcode
794 */
d7c0a89a 795void bgp_notify_send(struct peer *peer, uint8_t code, uint8_t sub_code)
718e3744 796{
d62a17ae 797 bgp_notify_send_with_data(peer, code, sub_code, NULL, 0);
718e3744 798}
799
d3ecc69e
QY
800/*
801 * Creates BGP Route Refresh packet and appends it to the peer's output queue.
802 *
803 * @param peer
804 * @param afi Address Family Identifier
805 * @param safi Subsequent Address Family Identifier
806 * @param orf_type Outbound Route Filtering type
807 * @param when_to_refresh Whether to refresh immediately or defer
808 * @param remove Whether to remove ORF for specified AFI/SAFI
809 */
d62a17ae 810void bgp_route_refresh_send(struct peer *peer, afi_t afi, safi_t safi,
d7c0a89a
QY
811 uint8_t orf_type, uint8_t when_to_refresh,
812 int remove)
718e3744 813{
d62a17ae 814 struct stream *s;
815 struct bgp_filter *filter;
816 int orf_refresh = 0;
817 iana_afi_t pkt_afi;
5c525538 818 iana_safi_t pkt_safi;
d62a17ae 819
820 if (DISABLE_BGP_ANNOUNCE)
821 return;
822
823 filter = &peer->filter[afi][safi];
824
825 /* Convert AFI, SAFI to values for packet. */
826 bgp_map_afi_safi_int2iana(afi, safi, &pkt_afi, &pkt_safi);
827
828 s = stream_new(BGP_MAX_PACKET_SIZE);
829
830 /* Make BGP update packet. */
831 if (CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_NEW_RCV))
832 bgp_packet_set_marker(s, BGP_MSG_ROUTE_REFRESH_NEW);
718e3744 833 else
d62a17ae 834 bgp_packet_set_marker(s, BGP_MSG_ROUTE_REFRESH_OLD);
835
836 /* Encode Route Refresh message. */
837 stream_putw(s, pkt_afi);
838 stream_putc(s, 0);
839 stream_putc(s, pkt_safi);
840
841 if (orf_type == ORF_TYPE_PREFIX || orf_type == ORF_TYPE_PREFIX_OLD)
842 if (remove || filter->plist[FILTER_IN].plist) {
d7c0a89a 843 uint16_t orf_len;
d62a17ae 844 unsigned long orfp;
845
846 orf_refresh = 1;
847 stream_putc(s, when_to_refresh);
848 stream_putc(s, orf_type);
849 orfp = stream_get_endp(s);
850 stream_putw(s, 0);
851
852 if (remove) {
853 UNSET_FLAG(peer->af_sflags[afi][safi],
854 PEER_STATUS_ORF_PREFIX_SEND);
855 stream_putc(s, ORF_COMMON_PART_REMOVE_ALL);
856 if (bgp_debug_neighbor_events(peer))
857 zlog_debug(
748a041f 858 "%s sending REFRESH_REQ to remove ORF(%d) (%s) for afi/safi: %s/%s",
d62a17ae 859 peer->host, orf_type,
860 (when_to_refresh == REFRESH_DEFER
861 ? "defer"
862 : "immediate"),
748a041f
DS
863 iana_afi2str(pkt_afi),
864 iana_safi2str(pkt_safi));
d62a17ae 865 } else {
866 SET_FLAG(peer->af_sflags[afi][safi],
867 PEER_STATUS_ORF_PREFIX_SEND);
868 prefix_bgp_orf_entry(
869 s, filter->plist[FILTER_IN].plist,
870 ORF_COMMON_PART_ADD,
871 ORF_COMMON_PART_PERMIT,
872 ORF_COMMON_PART_DENY);
873 if (bgp_debug_neighbor_events(peer))
874 zlog_debug(
748a041f 875 "%s sending REFRESH_REQ with pfxlist ORF(%d) (%s) for afi/safi: %s/%s",
d62a17ae 876 peer->host, orf_type,
877 (when_to_refresh == REFRESH_DEFER
878 ? "defer"
879 : "immediate"),
748a041f
DS
880 iana_afi2str(pkt_afi),
881 iana_safi2str(pkt_safi));
d62a17ae 882 }
883
884 /* Total ORF Entry Len. */
885 orf_len = stream_get_endp(s) - orfp - 2;
886 stream_putw_at(s, orfp, orf_len);
887 }
888
889 /* Set packet size. */
890 (void)bgp_packet_set_size(s);
891
892 if (bgp_debug_neighbor_events(peer)) {
893 if (!orf_refresh)
748a041f
DS
894 zlog_debug("%s sending REFRESH_REQ for afi/safi: %s/%s",
895 peer->host, iana_afi2str(pkt_afi),
896 iana_safi2str(pkt_safi));
d62a17ae 897 }
898
899 /* Add packet to the peer. */
900 bgp_packet_add(peer, s);
424ab01d
QY
901
902 bgp_writes_on(peer);
718e3744 903}
904
d3ecc69e
QY
905/*
906 * Create a BGP Capability packet and append it to the peer's output queue.
907 *
908 * @param peer
909 * @param afi Address Family Identifier
910 * @param safi Subsequent Address Family Identifier
911 * @param capability_code BGP Capability Code
912 * @param action Set or Remove capability
913 */
d62a17ae 914void bgp_capability_send(struct peer *peer, afi_t afi, safi_t safi,
915 int capability_code, int action)
718e3744 916{
d62a17ae 917 struct stream *s;
918 iana_afi_t pkt_afi;
5c525538 919 iana_safi_t pkt_safi;
d62a17ae 920
921 /* Convert AFI, SAFI to values for packet. */
922 bgp_map_afi_safi_int2iana(afi, safi, &pkt_afi, &pkt_safi);
923
924 s = stream_new(BGP_MAX_PACKET_SIZE);
925
926 /* Make BGP update packet. */
927 bgp_packet_set_marker(s, BGP_MSG_CAPABILITY);
928
929 /* Encode MP_EXT capability. */
930 if (capability_code == CAPABILITY_CODE_MP) {
931 stream_putc(s, action);
932 stream_putc(s, CAPABILITY_CODE_MP);
933 stream_putc(s, CAPABILITY_CODE_MP_LEN);
934 stream_putw(s, pkt_afi);
935 stream_putc(s, 0);
936 stream_putc(s, pkt_safi);
937
938 if (bgp_debug_neighbor_events(peer))
939 zlog_debug(
748a041f 940 "%s sending CAPABILITY has %s MP_EXT CAP for afi/safi: %s/%s",
d62a17ae 941 peer->host,
942 action == CAPABILITY_ACTION_SET ? "Advertising"
943 : "Removing",
748a041f 944 iana_afi2str(pkt_afi), iana_safi2str(pkt_safi));
d62a17ae 945 }
946
947 /* Set packet size. */
948 (void)bgp_packet_set_size(s);
718e3744 949
d62a17ae 950 /* Add packet to the peer. */
951 bgp_packet_add(peer, s);
424ab01d
QY
952
953 bgp_writes_on(peer);
d62a17ae 954}
718e3744 955
d62a17ae 956/* RFC1771 6.8 Connection collision detection. */
957static int bgp_collision_detect(struct peer *new, struct in_addr remote_id)
958{
959 struct peer *peer;
960
961 /* Upon receipt of an OPEN message, the local system must examine
962 all of its connections that are in the OpenConfirm state. A BGP
963 speaker may also examine connections in an OpenSent state if it
964 knows the BGP Identifier of the peer by means outside of the
965 protocol. If among these connections there is a connection to a
966 remote BGP speaker whose BGP Identifier equals the one in the
967 OPEN message, then the local system performs the following
968 collision resolution procedure: */
969
970 if ((peer = new->doppelganger) != NULL) {
971 /* Do not accept the new connection in Established or Clearing
972 * states.
973 * Note that a peer GR is handled by closing the existing
974 * connection
975 * upon receipt of new one.
976 */
977 if (peer->status == Established || peer->status == Clearing) {
978 bgp_notify_send(new, BGP_NOTIFY_CEASE,
979 BGP_NOTIFY_CEASE_COLLISION_RESOLUTION);
95f7965d 980 return -1;
d62a17ae 981 } else if ((peer->status == OpenConfirm)
982 || (peer->status == OpenSent)) {
787c3020
DA
983 /* 1. The BGP Identifier of the local system is
984 * compared to the BGP Identifier of the remote
985 * system (as specified in the OPEN message).
986 *
987 * If the BGP Identifiers of the peers
988 * involved in the connection collision
989 * are identical, then the connection
990 * initiated by the BGP speaker with the
991 * larger AS number is preserved.
992 */
d62a17ae 993 if (ntohl(peer->local_id.s_addr)
787c3020
DA
994 < ntohl(remote_id.s_addr)
995 || (ntohl(peer->local_id.s_addr)
996 == ntohl(remote_id.s_addr)
997 && peer->local_as < peer->as))
d62a17ae 998 if (!CHECK_FLAG(peer->sflags,
999 PEER_STATUS_ACCEPT_PEER)) {
1000 /* 2. If the value of the local BGP
1001 Identifier is less
1002 than the remote one, the local system
1003 closes BGP
1004 connection that already exists (the
1005 one that is
1006 already in the OpenConfirm state),
1007 and accepts BGP
1008 connection initiated by the remote
1009 system. */
1010 bgp_notify_send(
1011 peer, BGP_NOTIFY_CEASE,
1012 BGP_NOTIFY_CEASE_COLLISION_RESOLUTION);
1013 return 1;
1014 } else {
1015 bgp_notify_send(
1016 new, BGP_NOTIFY_CEASE,
1017 BGP_NOTIFY_CEASE_COLLISION_RESOLUTION);
1018 return -1;
1019 }
1020 else {
787c3020
DA
1021 if (ntohl(peer->local_id.s_addr)
1022 == ntohl(remote_id.s_addr)
1023 && peer->local_as == peer->as)
1024 flog_err(
1025 EC_BGP_ROUTER_ID_SAME,
23d0a753
DA
1026 "Peer's router-id %pI4 is the same as ours",
1027 &remote_id);
3dbe2b60 1028
d62a17ae 1029 /* 3. Otherwise, the local system closes newly
1030 created
1031 BGP connection (the one associated with the
1032 newly
1033 received OPEN message), and continues to use
1034 the
1035 existing one (the one that is already in the
1036 OpenConfirm state). */
1037 if (CHECK_FLAG(peer->sflags,
1038 PEER_STATUS_ACCEPT_PEER)) {
1039 bgp_notify_send(
1040 peer, BGP_NOTIFY_CEASE,
1041 BGP_NOTIFY_CEASE_COLLISION_RESOLUTION);
1042 return 1;
1043 } else {
1044 bgp_notify_send(
1045 new, BGP_NOTIFY_CEASE,
1046 BGP_NOTIFY_CEASE_COLLISION_RESOLUTION);
1047 return -1;
1048 }
1049 }
1050 }
1051 }
1052 return 0;
1053}
718e3744 1054
d8151687
QY
1055/* Packet processing routines ---------------------------------------------- */
1056/*
1057 * This is a family of functions designed to be called from
1058 * bgp_process_packet(). These functions all share similar behavior and should
1059 * adhere to the following invariants and restrictions:
1060 *
1061 * Return codes
1062 * ------------
1063 * The return code of any one of those functions should be one of the FSM event
1064 * codes specified in bgpd.h. If a NOTIFY was sent, this event code MUST be
1065 * BGP_Stop. Otherwise, the code SHOULD correspond to the function's expected
1066 * packet type. For example, bgp_open_receive() should return BGP_Stop upon
1067 * error and Receive_OPEN_message otherwise.
1068 *
1069 * If no action is necessary, the correct return code is BGP_PACKET_NOOP as
1070 * defined below.
1071 *
1072 * Side effects
1073 * ------------
1074 * - May send NOTIFY messages
1075 * - May not modify peer->status
1076 * - May not call bgp_event_update()
1077 */
1078
1079#define BGP_PACKET_NOOP 0
1080
1081/**
1082 * Process BGP OPEN message for peer.
1083 *
1084 * If any errors are encountered in the OPEN message, immediately sends NOTIFY
1085 * and returns BGP_Stop.
1086 *
1087 * @param peer
1088 * @param size size of the packet
1089 * @return as in summary
1090 */
d62a17ae 1091static int bgp_open_receive(struct peer *peer, bgp_size_t size)
1092{
1093 int ret;
d7c0a89a
QY
1094 uint8_t version;
1095 uint8_t optlen;
1096 uint16_t holdtime;
1097 uint16_t send_holdtime;
d62a17ae 1098 as_t remote_as;
6dcef54c 1099 as_t as4 = 0, as4_be;
d62a17ae 1100 struct in_addr remote_id;
1101 int mp_capability;
d7c0a89a
QY
1102 uint8_t notify_data_remote_as[2];
1103 uint8_t notify_data_remote_as4[4];
1104 uint8_t notify_data_remote_id[4];
1105 uint16_t *holdtime_ptr;
d62a17ae 1106
1107 /* Parse open packet. */
424ab01d
QY
1108 version = stream_getc(peer->curr);
1109 memcpy(notify_data_remote_as, stream_pnt(peer->curr), 2);
1110 remote_as = stream_getw(peer->curr);
d7c0a89a 1111 holdtime_ptr = (uint16_t *)stream_pnt(peer->curr);
424ab01d
QY
1112 holdtime = stream_getw(peer->curr);
1113 memcpy(notify_data_remote_id, stream_pnt(peer->curr), 4);
1114 remote_id.s_addr = stream_get_ipv4(peer->curr);
d62a17ae 1115
1116 /* Receive OPEN message log */
1117 if (bgp_debug_neighbor_events(peer))
1118 zlog_debug(
23d0a753
DA
1119 "%s rcv OPEN, version %d, remote-as (in open) %u, holdtime %d, id %pI4",
1120 peer->host, version, remote_as, holdtime, &remote_id);
d62a17ae 1121
1122 /* BEGIN to read the capability here, but dont do it yet */
1123 mp_capability = 0;
424ab01d 1124 optlen = stream_getc(peer->curr);
d62a17ae 1125
1126 if (optlen != 0) {
1127 /* If not enough bytes, it is an error. */
424ab01d 1128 if (STREAM_READABLE(peer->curr) < optlen) {
d62a17ae 1129 bgp_notify_send(peer, BGP_NOTIFY_OPEN_ERR,
1130 BGP_NOTIFY_OPEN_MALFORMED_ATTR);
d8151687 1131 return BGP_Stop;
d62a17ae 1132 }
718e3744 1133
d62a17ae 1134 /* We need the as4 capability value *right now* because
1135 * if it is there, we have not got the remote_as yet, and
1136 * without
1137 * that we do not know which peer is connecting to us now.
1138 */
1139 as4 = peek_for_as4_capability(peer, optlen);
d62a17ae 1140 }
718e3744 1141
6dcef54c
DL
1142 as4_be = htonl(as4);
1143 memcpy(notify_data_remote_as4, &as4_be, 4);
1144
d62a17ae 1145 /* Just in case we have a silly peer who sends AS4 capability set to 0
1146 */
1147 if (CHECK_FLAG(peer->cap, PEER_CAP_AS4_RCV) && !as4) {
e50f7cfd 1148 flog_err(EC_BGP_PKT_OPEN,
1c50c1c0
QY
1149 "%s bad OPEN, got AS4 capability, but AS4 set to 0",
1150 peer->host);
d62a17ae 1151 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1152 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1153 notify_data_remote_as4, 4);
d8151687 1154 return BGP_Stop;
d62a17ae 1155 }
718e3744 1156
33d022bc
DA
1157 /* Codification of AS 0 Processing */
1158 if (remote_as == BGP_AS_ZERO) {
1159 flog_err(EC_BGP_PKT_OPEN, "%s bad OPEN, got AS set to 0",
1160 peer->host);
1161 bgp_notify_send(peer, BGP_NOTIFY_OPEN_ERR,
1162 BGP_NOTIFY_OPEN_BAD_PEER_AS);
1163 return BGP_Stop;
1164 }
1165
d62a17ae 1166 if (remote_as == BGP_AS_TRANS) {
1167 /* Take the AS4 from the capability. We must have received the
1168 * capability now! Otherwise we have a asn16 peer who uses
1169 * BGP_AS_TRANS, for some unknown reason.
1170 */
1171 if (as4 == BGP_AS_TRANS) {
af4c2728 1172 flog_err(
e50f7cfd 1173 EC_BGP_PKT_OPEN,
d62a17ae 1174 "%s [AS4] NEW speaker using AS_TRANS for AS4, not allowed",
1175 peer->host);
1176 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1177 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1178 notify_data_remote_as4, 4);
d8151687 1179 return BGP_Stop;
d62a17ae 1180 }
718e3744 1181
d62a17ae 1182 if (!as4 && BGP_DEBUG(as4, AS4))
1183 zlog_debug(
3efd0893 1184 "%s [AS4] OPEN remote_as is AS_TRANS, but no AS4. Odd, but proceeding.",
d62a17ae 1185 peer->host);
1186 else if (as4 < BGP_AS_MAX && BGP_DEBUG(as4, AS4))
1187 zlog_debug(
3efd0893 1188 "%s [AS4] OPEN remote_as is AS_TRANS, but AS4 (%u) fits in 2-bytes, very odd peer.",
d62a17ae 1189 peer->host, as4);
1190 if (as4)
1191 remote_as = as4;
1192 } else {
1193 /* We may have a partner with AS4 who has an asno < BGP_AS_MAX
1194 */
1195 /* If we have got the capability, peer->as4cap must match
1196 * remote_as */
1197 if (CHECK_FLAG(peer->cap, PEER_CAP_AS4_RCV)
1198 && as4 != remote_as) {
1199 /* raise error, log this, close session */
af4c2728 1200 flog_err(
e50f7cfd 1201 EC_BGP_PKT_OPEN,
3efd0893 1202 "%s bad OPEN, got AS4 capability, but remote_as %u mismatch with 16bit 'myasn' %u in open",
d62a17ae 1203 peer->host, as4, remote_as);
1204 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1205 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1206 notify_data_remote_as4, 4);
d8151687 1207 return BGP_Stop;
d62a17ae 1208 }
1209 }
6b0655a2 1210
787c3020
DA
1211 /* rfc6286:
1212 * If the BGP Identifier field of the OPEN message
1213 * is zero, or if it is the same as the BGP Identifier
1214 * of the local BGP speaker and the message is from an
1215 * internal peer, then the Error Subcode is set to
1216 * "Bad BGP Identifier".
1217 */
975a328e 1218 if (remote_id.s_addr == INADDR_ANY
787c3020
DA
1219 || (peer->sort == BGP_PEER_IBGP
1220 && ntohl(peer->local_id.s_addr) == ntohl(remote_id.s_addr))) {
d62a17ae 1221 if (bgp_debug_neighbor_events(peer))
23d0a753
DA
1222 zlog_debug("%s bad OPEN, wrong router identifier %pI4",
1223 peer->host, &remote_id);
d62a17ae 1224 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1225 BGP_NOTIFY_OPEN_BAD_BGP_IDENT,
1226 notify_data_remote_id, 4);
d8151687 1227 return BGP_Stop;
d62a17ae 1228 }
1229
1230 /* Set remote router-id */
1231 peer->remote_id = remote_id;
1232
1233 /* Peer BGP version check. */
1234 if (version != BGP_VERSION_4) {
d7c0a89a 1235 uint16_t maxver = htons(BGP_VERSION_4);
d62a17ae 1236 /* XXX this reply may not be correct if version < 4 XXX */
1237 if (bgp_debug_neighbor_events(peer))
1238 zlog_debug(
1239 "%s bad protocol version, remote requested %d, local request %d",
1240 peer->host, version, BGP_VERSION_4);
1241 /* Data must be in network byte order here */
1242 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1243 BGP_NOTIFY_OPEN_UNSUP_VERSION,
d7c0a89a 1244 (uint8_t *)&maxver, 2);
d8151687 1245 return BGP_Stop;
d62a17ae 1246 }
1247
1248 /* Check neighbor as number. */
1249 if (peer->as_type == AS_UNSPECIFIED) {
1250 if (bgp_debug_neighbor_events(peer))
1251 zlog_debug(
1252 "%s bad OPEN, remote AS is unspecified currently",
1253 peer->host);
1254 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1255 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1256 notify_data_remote_as, 2);
d8151687 1257 return BGP_Stop;
d62a17ae 1258 } else if (peer->as_type == AS_INTERNAL) {
1259 if (remote_as != peer->bgp->as) {
1260 if (bgp_debug_neighbor_events(peer))
1261 zlog_debug(
1262 "%s bad OPEN, remote AS is %u, internal specified",
1263 peer->host, remote_as);
1264 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1265 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1266 notify_data_remote_as, 2);
d8151687 1267 return BGP_Stop;
1ff9a340 1268 }
d62a17ae 1269 peer->as = peer->local_as;
1270 } else if (peer->as_type == AS_EXTERNAL) {
1271 if (remote_as == peer->bgp->as) {
1272 if (bgp_debug_neighbor_events(peer))
1273 zlog_debug(
1274 "%s bad OPEN, remote AS is %u, external specified",
1275 peer->host, remote_as);
1276 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1277 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1278 notify_data_remote_as, 2);
d8151687 1279 return BGP_Stop;
1ff9a340 1280 }
d62a17ae 1281 peer->as = remote_as;
1282 } else if ((peer->as_type == AS_SPECIFIED) && (remote_as != peer->as)) {
1283 if (bgp_debug_neighbor_events(peer))
1284 zlog_debug("%s bad OPEN, remote AS is %u, expected %u",
1285 peer->host, remote_as, peer->as);
1286 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1287 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1288 notify_data_remote_as, 2);
d8151687 1289 return BGP_Stop;
eb821189 1290 }
718e3744 1291
d62a17ae 1292 /* From the rfc: Upon receipt of an OPEN message, a BGP speaker MUST
1293 calculate the value of the Hold Timer by using the smaller of its
1294 configured Hold Time and the Hold Time received in the OPEN message.
1295 The Hold Time MUST be either zero or at least three seconds. An
1296 implementation may reject connections on the basis of the Hold Time.
0b2aa3a0 1297 */
d62a17ae 1298
1299 if (holdtime < 3 && holdtime != 0) {
1300 bgp_notify_send_with_data(peer, BGP_NOTIFY_OPEN_ERR,
1301 BGP_NOTIFY_OPEN_UNACEP_HOLDTIME,
d7c0a89a 1302 (uint8_t *)holdtime_ptr, 2);
d8151687 1303 return BGP_Stop;
0b2aa3a0 1304 }
d62a17ae 1305
1306 /* From the rfc: A reasonable maximum time between KEEPALIVE messages
1307 would be one third of the Hold Time interval. KEEPALIVE messages
1308 MUST NOT be sent more frequently than one per second. An
1309 implementation MAY adjust the rate at which it sends KEEPALIVE
1310 messages as a function of the Hold Time interval. */
1311
b90a8e13 1312 if (CHECK_FLAG(peer->flags, PEER_FLAG_TIMER))
d62a17ae 1313 send_holdtime = peer->holdtime;
1314 else
1315 send_holdtime = peer->bgp->default_holdtime;
1316
1317 if (holdtime < send_holdtime)
1318 peer->v_holdtime = holdtime;
1319 else
1320 peer->v_holdtime = send_holdtime;
1321
7aa4fd5b
TA
1322 /* Set effective keepalive to 1/3 the effective holdtime.
1323 * Use configured keeplive when < effective keepalive.
1324 */
1325 peer->v_keepalive = peer->v_holdtime / 3;
1326 if (CHECK_FLAG(peer->flags, PEER_FLAG_TIMER)) {
1327 if (peer->keepalive && peer->keepalive < peer->v_keepalive)
1328 peer->v_keepalive = peer->keepalive;
1329 } else {
1330 if (peer->bgp->default_keepalive
1331 && peer->bgp->default_keepalive < peer->v_keepalive)
1332 peer->v_keepalive = peer->bgp->default_keepalive;
1333 }
d62a17ae 1334
1335 /* Open option part parse. */
1336 if (optlen != 0) {
1bb379bf 1337 if (bgp_open_option_parse(peer, optlen, &mp_capability) < 0)
d8151687 1338 return BGP_Stop;
d62a17ae 1339 } else {
1340 if (bgp_debug_neighbor_events(peer))
1341 zlog_debug("%s rcvd OPEN w/ OPTION parameter len: 0",
1342 peer->host);
0299c004 1343 }
d62a17ae 1344
1345 /*
1346 * Assume that the peer supports the locally configured set of
1347 * AFI/SAFIs if the peer did not send us any Mulitiprotocol
1348 * capabilities, or if 'override-capability' is configured.
1349 */
1350 if (!mp_capability
1351 || CHECK_FLAG(peer->flags, PEER_FLAG_OVERRIDE_CAPABILITY)) {
1352 peer->afc_nego[AFI_IP][SAFI_UNICAST] =
1353 peer->afc[AFI_IP][SAFI_UNICAST];
1354 peer->afc_nego[AFI_IP][SAFI_MULTICAST] =
1355 peer->afc[AFI_IP][SAFI_MULTICAST];
1356 peer->afc_nego[AFI_IP][SAFI_LABELED_UNICAST] =
1357 peer->afc[AFI_IP][SAFI_LABELED_UNICAST];
7c40bf39 1358 peer->afc_nego[AFI_IP][SAFI_FLOWSPEC] =
1359 peer->afc[AFI_IP][SAFI_FLOWSPEC];
d62a17ae 1360 peer->afc_nego[AFI_IP6][SAFI_UNICAST] =
1361 peer->afc[AFI_IP6][SAFI_UNICAST];
1362 peer->afc_nego[AFI_IP6][SAFI_MULTICAST] =
1363 peer->afc[AFI_IP6][SAFI_MULTICAST];
1364 peer->afc_nego[AFI_IP6][SAFI_LABELED_UNICAST] =
1365 peer->afc[AFI_IP6][SAFI_LABELED_UNICAST];
1366 peer->afc_nego[AFI_L2VPN][SAFI_EVPN] =
1367 peer->afc[AFI_L2VPN][SAFI_EVPN];
7c40bf39 1368 peer->afc_nego[AFI_IP6][SAFI_FLOWSPEC] =
1369 peer->afc[AFI_IP6][SAFI_FLOWSPEC];
0299c004 1370 }
d62a17ae 1371
036937f0
DA
1372 /* When collision is detected and this peer is closed.
1373 * Return immediately.
1374 */
d62a17ae 1375 ret = bgp_collision_detect(peer, remote_id);
1376 if (ret < 0)
d8151687 1377 return BGP_Stop;
d62a17ae 1378
1379 /* Get sockname. */
1bb379bf 1380 if (bgp_getsockname(peer) < 0) {
450971aa 1381 flog_err_sys(EC_LIB_SOCKET,
09c866e3 1382 "%s: bgp_getsockname() failed for peer: %s",
15569c58 1383 __func__, peer->host);
d8151687 1384 return BGP_Stop;
d62a17ae 1385 }
1386
1387 /* Verify valid local address present based on negotiated
1388 * address-families. */
1389 if (peer->afc_nego[AFI_IP][SAFI_UNICAST]
e5f22b30 1390 || peer->afc_nego[AFI_IP][SAFI_LABELED_UNICAST]
d62a17ae 1391 || peer->afc_nego[AFI_IP][SAFI_MULTICAST]
1392 || peer->afc_nego[AFI_IP][SAFI_MPLS_VPN]
1393 || peer->afc_nego[AFI_IP][SAFI_ENCAP]) {
975a328e 1394 if (peer->nexthop.v4.s_addr == INADDR_ANY) {
d62a17ae 1395#if defined(HAVE_CUMULUS)
50121ac0
DS
1396 zlog_warn("%s: No local IPv4 addr, BGP routing may not work",
1397 peer->host);
1d808091 1398#endif
d62a17ae 1399 }
1400 }
1401 if (peer->afc_nego[AFI_IP6][SAFI_UNICAST]
e5f22b30 1402 || peer->afc_nego[AFI_IP6][SAFI_LABELED_UNICAST]
d62a17ae 1403 || peer->afc_nego[AFI_IP6][SAFI_MULTICAST]
1404 || peer->afc_nego[AFI_IP6][SAFI_MPLS_VPN]
1405 || peer->afc_nego[AFI_IP6][SAFI_ENCAP]) {
1406 if (IN6_IS_ADDR_UNSPECIFIED(&peer->nexthop.v6_global)) {
1407#if defined(HAVE_CUMULUS)
50121ac0
DS
1408 zlog_warn("%s: No local IPv6 address, BGP routing may not work",
1409 peer->host);
1d808091 1410#endif
d62a17ae 1411 }
1412 }
1413 peer->rtt = sockopt_tcp_rtt(peer->fd);
1414
d8151687 1415 return Receive_OPEN_message;
718e3744 1416}
1417
d8151687
QY
1418/**
1419 * Process BGP KEEPALIVE message for peer.
1420 *
1421 * @param peer
1422 * @param size size of the packet
1423 * @return as in summary
1424 */
1425static int bgp_keepalive_receive(struct peer *peer, bgp_size_t size)
f188f2c4 1426{
d8151687
QY
1427 if (bgp_debug_keepalive(peer))
1428 zlog_debug("%s KEEPALIVE rcvd", peer->host);
d62a17ae 1429
d8151687 1430 bgp_update_implicit_eors(peer);
d62a17ae 1431
e410d563
DA
1432 peer->rtt = sockopt_tcp_rtt(peer->fd);
1433
8336c896
DA
1434 /* If the peer's RTT is higher than expected, shutdown
1435 * the peer automatically.
1436 */
1437 if (CHECK_FLAG(peer->flags, PEER_FLAG_RTT_SHUTDOWN)
1438 && peer->rtt > peer->rtt_expected) {
1439
1440 peer->rtt_keepalive_rcv++;
1441
1442 if (peer->rtt_keepalive_rcv > peer->rtt_keepalive_conf) {
1443 zlog_warn(
1444 "%s shutdown due to high round-trip-time (%dms > %dms)",
1445 peer->host, peer->rtt, peer->rtt_expected);
1446 peer_flag_set(peer, PEER_FLAG_SHUTDOWN);
1447 }
1448 } else {
1449 if (peer->rtt_keepalive_rcv)
1450 peer->rtt_keepalive_rcv--;
1451 }
1452
d8151687 1453 return Receive_KEEPALIVE_message;
f188f2c4
DS
1454}
1455
d62a17ae 1456
d8151687
QY
1457/**
1458 * Process BGP UPDATE message for peer.
1459 *
1460 * Parses UPDATE and creates attribute object.
1461 *
1462 * @param peer
1463 * @param size size of the packet
1464 * @return as in summary
7ef5a232 1465 */
d62a17ae 1466static int bgp_update_receive(struct peer *peer, bgp_size_t size)
718e3744 1467{
d62a17ae 1468 int ret, nlri_ret;
d7c0a89a 1469 uint8_t *end;
d62a17ae 1470 struct stream *s;
1471 struct attr attr;
1472 bgp_size_t attribute_len;
1473 bgp_size_t update_len;
1474 bgp_size_t withdraw_len;
f009ff26 1475 bool restart = false;
d62a17ae 1476
1477 enum NLRI_TYPES {
1478 NLRI_UPDATE,
1479 NLRI_WITHDRAW,
1480 NLRI_MP_UPDATE,
1481 NLRI_MP_WITHDRAW,
1482 NLRI_TYPE_MAX
1483 };
1484 struct bgp_nlri nlris[NLRI_TYPE_MAX];
1485
1486 /* Status must be Established. */
1487 if (peer->status != Established) {
e50f7cfd 1488 flog_err(EC_BGP_INVALID_STATUS,
1c50c1c0
QY
1489 "%s [FSM] Update packet received under status %s",
1490 peer->host,
1491 lookup_msg(bgp_status_msg, peer->status, NULL));
0e35025e 1492 bgp_notify_send(peer, BGP_NOTIFY_FSM_ERR,
3893aeee 1493 bgp_fsm_error_subcode(peer->status));
d8151687 1494 return BGP_Stop;
d62a17ae 1495 }
1496
1497 /* Set initial values. */
1498 memset(&attr, 0, sizeof(struct attr));
1499 attr.label_index = BGP_INVALID_LABEL_INDEX;
1500 attr.label = MPLS_INVALID_LABEL;
1501 memset(&nlris, 0, sizeof(nlris));
1502 memset(peer->rcvd_attr_str, 0, BUFSIZ);
1503 peer->rcvd_attr_printed = 0;
1504
424ab01d 1505 s = peer->curr;
d62a17ae 1506 end = stream_pnt(s) + size;
1507
1508 /* RFC1771 6.3 If the Unfeasible Routes Length or Total Attribute
1509 Length is too large (i.e., if Unfeasible Routes Length + Total
1510 Attribute Length + 23 exceeds the message Length), then the Error
1511 Subcode is set to Malformed Attribute List. */
1512 if (stream_pnt(s) + 2 > end) {
e50f7cfd 1513 flog_err(EC_BGP_UPDATE_RCV,
3efd0893 1514 "%s [Error] Update packet error (packet length is short for unfeasible length)",
1c50c1c0 1515 peer->host);
d62a17ae 1516 bgp_notify_send(peer, BGP_NOTIFY_UPDATE_ERR,
1517 BGP_NOTIFY_UPDATE_MAL_ATTR);
d8151687 1518 return BGP_Stop;
d62a17ae 1519 }
1520
1521 /* Unfeasible Route Length. */
1522 withdraw_len = stream_getw(s);
1523
1524 /* Unfeasible Route Length check. */
1525 if (stream_pnt(s) + withdraw_len > end) {
e50f7cfd 1526 flog_err(EC_BGP_UPDATE_RCV,
3efd0893 1527 "%s [Error] Update packet error (packet unfeasible length overflow %d)",
1c50c1c0 1528 peer->host, withdraw_len);
d62a17ae 1529 bgp_notify_send(peer, BGP_NOTIFY_UPDATE_ERR,
1530 BGP_NOTIFY_UPDATE_MAL_ATTR);
d8151687 1531 return BGP_Stop;
d62a17ae 1532 }
1533
1534 /* Unfeasible Route packet format check. */
1535 if (withdraw_len > 0) {
1536 nlris[NLRI_WITHDRAW].afi = AFI_IP;
1537 nlris[NLRI_WITHDRAW].safi = SAFI_UNICAST;
1538 nlris[NLRI_WITHDRAW].nlri = stream_pnt(s);
1539 nlris[NLRI_WITHDRAW].length = withdraw_len;
1540 stream_forward_getp(s, withdraw_len);
1541 }
1542
1543 /* Attribute total length check. */
1544 if (stream_pnt(s) + 2 > end) {
ade6974d 1545 flog_warn(
e50f7cfd 1546 EC_BGP_UPDATE_PACKET_SHORT,
ade6974d
QY
1547 "%s [Error] Packet Error (update packet is short for attribute length)",
1548 peer->host);
d62a17ae 1549 bgp_notify_send(peer, BGP_NOTIFY_UPDATE_ERR,
1550 BGP_NOTIFY_UPDATE_MAL_ATTR);
d8151687 1551 return BGP_Stop;
d62a17ae 1552 }
1553
1554 /* Fetch attribute total length. */
1555 attribute_len = stream_getw(s);
1556
1557 /* Attribute length check. */
1558 if (stream_pnt(s) + attribute_len > end) {
ade6974d 1559 flog_warn(
e50f7cfd 1560 EC_BGP_UPDATE_PACKET_LONG,
ade6974d
QY
1561 "%s [Error] Packet Error (update packet attribute length overflow %d)",
1562 peer->host, attribute_len);
d62a17ae 1563 bgp_notify_send(peer, BGP_NOTIFY_UPDATE_ERR,
1564 BGP_NOTIFY_UPDATE_MAL_ATTR);
d8151687 1565 return BGP_Stop;
d62a17ae 1566 }
1567
1568 /* Certain attribute parsing errors should not be considered bad enough
1569 * to reset the session for, most particularly any partial/optional
1570 * attributes that have 'tunneled' over speakers that don't understand
1571 * them. Instead we withdraw only the prefix concerned.
1572 *
1573 * Complicates the flow a little though..
1574 */
1575 bgp_attr_parse_ret_t attr_parse_ret = BGP_ATTR_PARSE_PROCEED;
1576/* This define morphs the update case into a withdraw when lower levels
1577 * have signalled an error condition where this is best.
1578 */
b881c707 1579#define NLRI_ATTR_ARG (attr_parse_ret != BGP_ATTR_PARSE_WITHDRAW ? &attr : NULL)
718e3744 1580
d62a17ae 1581 /* Parse attribute when it exists. */
1582 if (attribute_len) {
1583 attr_parse_ret = bgp_attr_parse(peer, &attr, attribute_len,
1584 &nlris[NLRI_MP_UPDATE],
1585 &nlris[NLRI_MP_WITHDRAW]);
1586 if (attr_parse_ret == BGP_ATTR_PARSE_ERROR) {
1587 bgp_attr_unintern_sub(&attr);
d8151687 1588 return BGP_Stop;
d62a17ae 1589 }
1590 }
1591
1592 /* Logging the attribute. */
1593 if (attr_parse_ret == BGP_ATTR_PARSE_WITHDRAW
1594 || BGP_DEBUG(update, UPDATE_IN)
1595 || BGP_DEBUG(update, UPDATE_PREFIX)) {
5022c833
DA
1596 ret = bgp_dump_attr(&attr, peer->rcvd_attr_str,
1597 sizeof(peer->rcvd_attr_str));
d62a17ae 1598
b4d46cc9
DL
1599 peer->stat_upd_7606++;
1600
d62a17ae 1601 if (attr_parse_ret == BGP_ATTR_PARSE_WITHDRAW)
af4c2728 1602 flog_err(
e50f7cfd 1603 EC_BGP_UPDATE_RCV,
d62a17ae 1604 "%s rcvd UPDATE with errors in attr(s)!! Withdrawing route.",
1605 peer->host);
1606
1607 if (ret && bgp_debug_update(peer, NULL, NULL, 1)) {
1608 zlog_debug("%s rcvd UPDATE w/ attr: %s", peer->host,
1609 peer->rcvd_attr_str);
1610 peer->rcvd_attr_printed = 1;
1611 }
1612 }
1613
1614 /* Network Layer Reachability Information. */
1615 update_len = end - stream_pnt(s);
1616
1617 if (update_len) {
1618 /* Set NLRI portion to structure. */
1619 nlris[NLRI_UPDATE].afi = AFI_IP;
1620 nlris[NLRI_UPDATE].safi = SAFI_UNICAST;
1621 nlris[NLRI_UPDATE].nlri = stream_pnt(s);
1622 nlris[NLRI_UPDATE].length = update_len;
1623 stream_forward_getp(s, update_len);
9738e9aa 1624
1625 if (CHECK_FLAG(attr.flag, ATTR_FLAG_BIT(BGP_ATTR_MP_REACH_NLRI))) {
1626 /*
1627 * We skipped nexthop attribute validation earlier so
1628 * validate the nexthop now.
1629 */
1630 if (bgp_attr_nexthop_valid(peer, &attr) < 0) {
1631 bgp_attr_unintern_sub(&attr);
1632 return BGP_Stop;
1633 }
1634 }
d62a17ae 1635 }
1636
1637 if (BGP_DEBUG(update, UPDATE_IN))
1638 zlog_debug("%s rcvd UPDATE wlen %d attrlen %d alen %d",
1639 peer->host, withdraw_len, attribute_len, update_len);
1640
1641 /* Parse any given NLRIs */
1642 for (int i = NLRI_UPDATE; i < NLRI_TYPE_MAX; i++) {
1643 if (!nlris[i].nlri)
1644 continue;
1645
1646 /* NLRI is processed iff the peer if configured for the specific
1647 * afi/safi */
1648 if (!peer->afc[nlris[i].afi][nlris[i].safi]) {
1649 zlog_info(
1650 "%s [Info] UPDATE for non-enabled AFI/SAFI %u/%u",
1651 peer->host, nlris[i].afi, nlris[i].safi);
1652 continue;
1653 }
1654
1655 /* EoR handled later */
1656 if (nlris[i].length == 0)
1657 continue;
1658
1659 switch (i) {
1660 case NLRI_UPDATE:
1661 case NLRI_MP_UPDATE:
1662 nlri_ret = bgp_nlri_parse(peer, NLRI_ATTR_ARG,
1663 &nlris[i], 0);
1664 break;
1665 case NLRI_WITHDRAW:
1666 case NLRI_MP_WITHDRAW:
1667 nlri_ret = bgp_nlri_parse(peer, &attr, &nlris[i], 1);
1668 break;
1669 default:
513386b5 1670 nlri_ret = BGP_NLRI_PARSE_ERROR;
d62a17ae 1671 }
1672
513386b5
DA
1673 if (nlri_ret < BGP_NLRI_PARSE_OK
1674 && nlri_ret != BGP_NLRI_PARSE_ERROR_PREFIX_OVERFLOW) {
e50f7cfd 1675 flog_err(EC_BGP_UPDATE_RCV,
1c50c1c0 1676 "%s [Error] Error parsing NLRI", peer->host);
d62a17ae 1677 if (peer->status == Established)
1678 bgp_notify_send(
1679 peer, BGP_NOTIFY_UPDATE_ERR,
1680 i <= NLRI_WITHDRAW
1681 ? BGP_NOTIFY_UPDATE_INVAL_NETWORK
1682 : BGP_NOTIFY_UPDATE_OPT_ATTR_ERR);
1683 bgp_attr_unintern_sub(&attr);
d8151687 1684 return BGP_Stop;
d62a17ae 1685 }
1686 }
1687
1688 /* EoR checks
1689 *
1690 * Non-MP IPv4/Unicast EoR is a completely empty UPDATE
1691 * and MP EoR should have only an empty MP_UNREACH
1692 */
996c9314
LB
1693 if ((!update_len && !withdraw_len && nlris[NLRI_MP_UPDATE].length == 0)
1694 || (attr_parse_ret == BGP_ATTR_PARSE_EOR)) {
d62a17ae 1695 afi_t afi = 0;
1696 safi_t safi;
f009ff26 1697 struct graceful_restart_info *gr_info;
1698
1699 /* Restarting router */
36235319
QY
1700 if (BGP_PEER_GRACEFUL_RESTART_CAPABLE(peer)
1701 && BGP_PEER_RESTARTING_MODE(peer))
f009ff26 1702 restart = true;
d62a17ae 1703
1704 /* Non-MP IPv4/Unicast is a completely emtpy UPDATE - already
1705 * checked
1706 * update and withdraw NLRI lengths are 0.
1707 */
1708 if (!attribute_len) {
1709 afi = AFI_IP;
1710 safi = SAFI_UNICAST;
1711 } else if (attr.flag & ATTR_FLAG_BIT(BGP_ATTR_MP_UNREACH_NLRI)
1712 && nlris[NLRI_MP_WITHDRAW].length == 0) {
1713 afi = nlris[NLRI_MP_WITHDRAW].afi;
1714 safi = nlris[NLRI_MP_WITHDRAW].safi;
9b9df989
DS
1715 } else if (attr_parse_ret == BGP_ATTR_PARSE_EOR) {
1716 afi = nlris[NLRI_MP_UPDATE].afi;
1717 safi = nlris[NLRI_MP_UPDATE].safi;
d62a17ae 1718 }
1719
1720 if (afi && peer->afc[afi][safi]) {
e82d19a3
DS
1721 struct vrf *vrf = vrf_lookup_by_id(peer->bgp->vrf_id);
1722
d62a17ae 1723 /* End-of-RIB received */
1724 if (!CHECK_FLAG(peer->af_sflags[afi][safi],
1725 PEER_STATUS_EOR_RECEIVED)) {
1726 SET_FLAG(peer->af_sflags[afi][safi],
1727 PEER_STATUS_EOR_RECEIVED);
1728 bgp_update_explicit_eors(peer);
f009ff26 1729 /* Update graceful restart information */
1730 gr_info = &(peer->bgp->gr_info[afi][safi]);
1731 if (restart)
1732 gr_info->eor_received++;
1733 /* If EOR received from all peers and selection
1734 * deferral timer is running, cancel the timer
1735 * and invoke the best path calculation
1736 */
36235319
QY
1737 if (gr_info->eor_required
1738 == gr_info->eor_received) {
1739 if (bgp_debug_neighbor_events(peer))
1740 zlog_debug(
1741 "%s %d, %s %d",
f009ff26 1742 "EOR REQ",
1743 gr_info->eor_required,
1744 "EOR RCV",
1745 gr_info->eor_received);
1746 BGP_TIMER_OFF(
1747 gr_info->t_select_deferral);
1748 gr_info->eor_required = 0;
1749 gr_info->eor_received = 0;
1750 /* Best path selection */
1751 if (bgp_best_path_select_defer(
36235319
QY
1752 peer->bgp, afi, safi)
1753 < 0)
f009ff26 1754 return BGP_Stop;
1755 }
d62a17ae 1756 }
1757
1758 /* NSF delete stale route */
1759 if (peer->nsf[afi][safi])
1760 bgp_clear_stale_route(peer, afi, safi);
1761
a0e89d54
TA
1762 zlog_info(
1763 "%s: rcvd End-of-RIB for %s from %s in vrf %s",
1764 __func__, get_afi_safi_str(afi, safi, false),
1765 peer->host, vrf ? vrf->name : VRF_DEFAULT_NAME);
1766 }
f80f838b 1767 }
d62a17ae 1768
1769 /* Everything is done. We unintern temporary structures which
1770 interned in bgp_attr_parse(). */
1771 bgp_attr_unintern_sub(&attr);
1772
d62a17ae 1773 peer->update_time = bgp_clock();
1774
c385f82a
MK
1775 /* Notify BGP Conditional advertisement scanner process */
1776 peer->advmap_table_change = true;
1777
d8151687 1778 return Receive_UPDATE_message;
718e3744 1779}
1780
d8151687
QY
1781/**
1782 * Process BGP NOTIFY message for peer.
1783 *
1784 * @param peer
1785 * @param size size of the packet
1786 * @return as in summary
1787 */
1788static int bgp_notify_receive(struct peer *peer, bgp_size_t size)
718e3744 1789{
d62a17ae 1790 struct bgp_notify bgp_notify;
1791
1792 if (peer->notify.data) {
1793 XFREE(MTYPE_TMP, peer->notify.data);
d62a17ae 1794 peer->notify.length = 0;
1795 }
1796
424ab01d
QY
1797 bgp_notify.code = stream_getc(peer->curr);
1798 bgp_notify.subcode = stream_getc(peer->curr);
d62a17ae 1799 bgp_notify.length = size - 2;
1800 bgp_notify.data = NULL;
1801
1802 /* Preserv notify code and sub code. */
1803 peer->notify.code = bgp_notify.code;
1804 peer->notify.subcode = bgp_notify.subcode;
1805 /* For further diagnostic record returned Data. */
1806 if (bgp_notify.length) {
1807 peer->notify.length = size - 2;
1808 peer->notify.data = XMALLOC(MTYPE_TMP, size - 2);
424ab01d 1809 memcpy(peer->notify.data, stream_pnt(peer->curr), size - 2);
d62a17ae 1810 }
1811
1812 /* For debug */
1813 {
1814 int i;
1815 int first = 0;
1816 char c[4];
1817
1818 if (bgp_notify.length) {
1819 bgp_notify.data =
1820 XMALLOC(MTYPE_TMP, bgp_notify.length * 3);
1821 for (i = 0; i < bgp_notify.length; i++)
1822 if (first) {
552d6491 1823 snprintf(c, sizeof(c), " %02x",
424ab01d 1824 stream_getc(peer->curr));
f009ff26 1825
552d6491 1826 strlcat(bgp_notify.data, c,
f009ff26 1827 bgp_notify.length * 3);
1828
d62a17ae 1829 } else {
1830 first = 1;
552d6491
QY
1831 snprintf(c, sizeof(c), "%02x",
1832 stream_getc(peer->curr));
f009ff26 1833
552d6491 1834 strlcpy(bgp_notify.data, c,
f009ff26 1835 bgp_notify.length * 3);
d62a17ae 1836 }
d7c0a89a 1837 bgp_notify.raw_data = (uint8_t *)peer->notify.data;
d62a17ae 1838 }
1839
1840 bgp_notify_print(peer, &bgp_notify, "received");
1841 if (bgp_notify.data) {
1842 XFREE(MTYPE_TMP, bgp_notify.data);
d62a17ae 1843 bgp_notify.length = 0;
1844 }
1845 }
1846
1847 /* peer count update */
0112e9e0 1848 atomic_fetch_add_explicit(&peer->notify_in, 1, memory_order_relaxed);
d62a17ae 1849
1850 peer->last_reset = PEER_DOWN_NOTIFY_RECEIVED;
1851
1852 /* We have to check for Notify with Unsupported Optional Parameter.
1853 in that case we fallback to open without the capability option.
1854 But this done in bgp_stop. We just mark it here to avoid changing
1855 the fsm tables. */
1856 if (bgp_notify.code == BGP_NOTIFY_OPEN_ERR
1857 && bgp_notify.subcode == BGP_NOTIFY_OPEN_UNSUP_PARAM)
1858 UNSET_FLAG(peer->sflags, PEER_STATUS_CAPABILITY_OPEN);
1859
5cce3f05 1860 bgp_peer_gr_flags_update(peer);
36235319
QY
1861 BGP_GR_ROUTER_DETECT_AND_SEND_CAPABILITY_TO_ZEBRA(peer->bgp,
1862 peer->bgp->peer);
5cce3f05 1863
d8151687 1864 return Receive_NOTIFICATION_message;
718e3744 1865}
1866
d8151687
QY
1867/**
1868 * Process BGP ROUTEREFRESH message for peer.
1869 *
1870 * @param peer
1871 * @param size size of the packet
1872 * @return as in summary
1873 */
1874static int bgp_route_refresh_receive(struct peer *peer, bgp_size_t size)
718e3744 1875{
d62a17ae 1876 iana_afi_t pkt_afi;
1877 afi_t afi;
5c525538
RW
1878 iana_safi_t pkt_safi;
1879 safi_t safi;
d62a17ae 1880 struct stream *s;
1881 struct peer_af *paf;
1882 struct update_group *updgrp;
1883 struct peer *updgrp_peer;
1884
1885 /* If peer does not have the capability, send notification. */
1886 if (!CHECK_FLAG(peer->cap, PEER_CAP_REFRESH_ADV)) {
e50f7cfd 1887 flog_err(EC_BGP_NO_CAP,
1c50c1c0
QY
1888 "%s [Error] BGP route refresh is not enabled",
1889 peer->host);
d62a17ae 1890 bgp_notify_send(peer, BGP_NOTIFY_HEADER_ERR,
1891 BGP_NOTIFY_HEADER_BAD_MESTYPE);
d8151687 1892 return BGP_Stop;
d62a17ae 1893 }
1894
1895 /* Status must be Established. */
1896 if (peer->status != Established) {
af4c2728 1897 flog_err(
e50f7cfd 1898 EC_BGP_INVALID_STATUS,
d62a17ae 1899 "%s [Error] Route refresh packet received under status %s",
1900 peer->host,
1901 lookup_msg(bgp_status_msg, peer->status, NULL));
0e35025e 1902 bgp_notify_send(peer, BGP_NOTIFY_FSM_ERR,
3893aeee 1903 bgp_fsm_error_subcode(peer->status));
d8151687 1904 return BGP_Stop;
d62a17ae 1905 }
1906
424ab01d 1907 s = peer->curr;
d62a17ae 1908
1909 /* Parse packet. */
1910 pkt_afi = stream_getw(s);
1911 (void)stream_getc(s);
1912 pkt_safi = stream_getc(s);
1913
1914 if (bgp_debug_update(peer, NULL, NULL, 0))
748a041f
DS
1915 zlog_debug("%s rcvd REFRESH_REQ for afi/safi: %s/%s",
1916 peer->host, iana_afi2str(pkt_afi),
1917 iana_safi2str(pkt_safi));
d62a17ae 1918
1919 /* Convert AFI, SAFI to internal values and check. */
1920 if (bgp_map_afi_safi_iana2int(pkt_afi, pkt_safi, &afi, &safi)) {
1921 zlog_info(
748a041f
DS
1922 "%s REFRESH_REQ for unrecognized afi/safi: %s/%s - ignored",
1923 peer->host, iana_afi2str(pkt_afi),
1924 iana_safi2str(pkt_safi));
d8151687 1925 return BGP_PACKET_NOOP;
d62a17ae 1926 }
1927
1928 if (size != BGP_MSG_ROUTE_REFRESH_MIN_SIZE - BGP_HEADER_SIZE) {
d7c0a89a
QY
1929 uint8_t *end;
1930 uint8_t when_to_refresh;
1931 uint8_t orf_type;
1932 uint16_t orf_len;
d62a17ae 1933
1934 if (size - (BGP_MSG_ROUTE_REFRESH_MIN_SIZE - BGP_HEADER_SIZE)
1935 < 5) {
1936 zlog_info("%s ORF route refresh length error",
1937 peer->host);
0e35025e
DA
1938 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
1939 BGP_NOTIFY_SUBCODE_UNSPECIFIC);
d8151687 1940 return BGP_Stop;
718e3744 1941 }
1942
d62a17ae 1943 when_to_refresh = stream_getc(s);
1944 end = stream_pnt(s) + (size - 5);
1945
1946 while ((stream_pnt(s) + 2) < end) {
1947 orf_type = stream_getc(s);
1948 orf_len = stream_getw(s);
1949
1950 /* orf_len in bounds? */
1951 if ((stream_pnt(s) + orf_len) > end)
1952 break; /* XXX: Notify instead?? */
1953 if (orf_type == ORF_TYPE_PREFIX
1954 || orf_type == ORF_TYPE_PREFIX_OLD) {
1955 uint8_t *p_pnt = stream_pnt(s);
1956 uint8_t *p_end = stream_pnt(s) + orf_len;
1957 struct orf_prefix orfp;
d7c0a89a
QY
1958 uint8_t common = 0;
1959 uint32_t seq;
d62a17ae 1960 int psize;
1961 char name[BUFSIZ];
1962 int ret = CMD_SUCCESS;
1963
1964 if (bgp_debug_neighbor_events(peer)) {
1965 zlog_debug(
1966 "%s rcvd Prefixlist ORF(%d) length %d",
1967 peer->host, orf_type, orf_len);
1968 }
1969
1970 /* we're going to read at least 1 byte of common
1971 * ORF header,
1972 * and 7 bytes of ORF Address-filter entry from
1973 * the stream
1974 */
1975 if (orf_len < 7)
1976 break;
1977
1978 /* ORF prefix-list name */
772270f3
QY
1979 snprintf(name, sizeof(name), "%s.%d.%d",
1980 peer->host, afi, safi);
d62a17ae 1981
1982 while (p_pnt < p_end) {
1983 /* If the ORF entry is malformed, want
1984 * to read as much of it
1985 * as possible without going beyond the
1986 * bounds of the entry,
1987 * to maximise debug information.
1988 */
1989 int ok;
1990 memset(&orfp, 0,
1991 sizeof(struct orf_prefix));
1992 common = *p_pnt++;
1993 /* after ++: p_pnt <= p_end */
1994 if (common
1995 & ORF_COMMON_PART_REMOVE_ALL) {
1996 if (bgp_debug_neighbor_events(
1997 peer))
1998 zlog_debug(
1999 "%s rcvd Remove-All pfxlist ORF request",
2000 peer->host);
2001 prefix_bgp_orf_remove_all(afi,
2002 name);
2003 break;
2004 }
d7c0a89a
QY
2005 ok = ((uint32_t)(p_end - p_pnt)
2006 >= sizeof(uint32_t));
d62a17ae 2007 if (ok) {
2008 memcpy(&seq, p_pnt,
d7c0a89a
QY
2009 sizeof(uint32_t));
2010 p_pnt += sizeof(uint32_t);
d62a17ae 2011 orfp.seq = ntohl(seq);
2012 } else
2013 p_pnt = p_end;
2014
5ca840a3 2015 /* val checked in prefix_bgp_orf_set */
1bb379bf 2016 if (p_pnt < p_end)
5ca840a3
DS
2017 orfp.ge = *p_pnt++;
2018
2019 /* val checked in prefix_bgp_orf_set */
1bb379bf 2020 if (p_pnt < p_end)
5ca840a3
DS
2021 orfp.le = *p_pnt++;
2022
d62a17ae 2023 if ((ok = (p_pnt < p_end)))
2024 orfp.p.prefixlen = *p_pnt++;
5ca840a3
DS
2025
2026 /* afi checked already */
2027 orfp.p.family = afi2family(afi);
2028
2029 /* 0 if not ok */
2030 psize = PSIZE(orfp.p.prefixlen);
2031 /* valid for family ? */
2032 if (psize > prefix_blen(&orfp.p)) {
d62a17ae 2033 ok = 0;
2034 psize = prefix_blen(&orfp.p);
2035 }
5ca840a3
DS
2036 /* valid for packet ? */
2037 if (psize > (p_end - p_pnt)) {
d62a17ae 2038 ok = 0;
2039 psize = p_end - p_pnt;
2040 }
2041
2042 if (psize > 0)
2043 memcpy(&orfp.p.u.prefix, p_pnt,
2044 psize);
2045 p_pnt += psize;
2046
2047 if (bgp_debug_neighbor_events(peer)) {
2048 char buf[INET6_BUFSIZ];
2049
2050 zlog_debug(
2051 "%s rcvd %s %s seq %u %s/%d ge %d le %d%s",
2052 peer->host,
2053 (common & ORF_COMMON_PART_REMOVE
2054 ? "Remove"
2055 : "Add"),
2056 (common & ORF_COMMON_PART_DENY
2057 ? "deny"
2058 : "permit"),
2059 orfp.seq,
2060 inet_ntop(
2061 orfp.p.family,
2062 &orfp.p.u.prefix,
2063 buf,
2064 INET6_BUFSIZ),
2065 orfp.p.prefixlen,
2066 orfp.ge, orfp.le,
2067 ok ? "" : " MALFORMED");
2068 }
2069
2070 if (ok)
2071 ret = prefix_bgp_orf_set(
2072 name, afi, &orfp,
2073 (common & ORF_COMMON_PART_DENY
2074 ? 0
2075 : 1),
2076 (common & ORF_COMMON_PART_REMOVE
2077 ? 0
2078 : 1));
2079
2080 if (!ok || (ok && ret != CMD_SUCCESS)) {
2081 zlog_info(
3efd0893 2082 "%s Received misformatted prefixlist ORF. Remove All pfxlist",
d62a17ae 2083 peer->host);
2084 prefix_bgp_orf_remove_all(afi,
2085 name);
2086 break;
2087 }
2088 }
2089
2090 peer->orf_plist[afi][safi] =
2091 prefix_bgp_orf_lookup(afi, name);
2092 }
2093 stream_forward_getp(s, orf_len);
718e3744 2094 }
d62a17ae 2095 if (bgp_debug_neighbor_events(peer))
2096 zlog_debug("%s rcvd Refresh %s ORF request", peer->host,
2097 when_to_refresh == REFRESH_DEFER
2098 ? "Defer"
2099 : "Immediate");
2100 if (when_to_refresh == REFRESH_DEFER)
d8151687 2101 return BGP_PACKET_NOOP;
d62a17ae 2102 }
40d2700d 2103
d62a17ae 2104 /* First update is deferred until ORF or ROUTE-REFRESH is received */
2105 if (CHECK_FLAG(peer->af_sflags[afi][safi],
2106 PEER_STATUS_ORF_WAIT_REFRESH))
2107 UNSET_FLAG(peer->af_sflags[afi][safi],
2108 PEER_STATUS_ORF_WAIT_REFRESH);
2109
2110 paf = peer_af_find(peer, afi, safi);
2111 if (paf && paf->subgroup) {
2112 if (peer->orf_plist[afi][safi]) {
2113 updgrp = PAF_UPDGRP(paf);
2114 updgrp_peer = UPDGRP_PEER(updgrp);
2115 updgrp_peer->orf_plist[afi][safi] =
2116 peer->orf_plist[afi][safi];
2117 }
2118
2119 /* If the peer is configured for default-originate clear the
2120 * SUBGRP_STATUS_DEFAULT_ORIGINATE flag so that we will
2121 * re-advertise the
2122 * default
2123 */
2124 if (CHECK_FLAG(paf->subgroup->sflags,
2125 SUBGRP_STATUS_DEFAULT_ORIGINATE))
2126 UNSET_FLAG(paf->subgroup->sflags,
2127 SUBGRP_STATUS_DEFAULT_ORIGINATE);
718e3744 2128 }
d62a17ae 2129
2130 /* Perform route refreshment to the peer */
2131 bgp_announce_route(peer, afi, safi);
d8151687
QY
2132
2133 /* No FSM action necessary */
2134 return BGP_PACKET_NOOP;
718e3744 2135}
2136
d8151687
QY
2137/**
2138 * Parse BGP CAPABILITY message for peer.
2139 *
2140 * @param peer
2141 * @param size size of the packet
2142 * @return as in summary
2143 */
d7c0a89a 2144static int bgp_capability_msg_parse(struct peer *peer, uint8_t *pnt,
d62a17ae 2145 bgp_size_t length)
718e3744 2146{
d7c0a89a 2147 uint8_t *end;
d62a17ae 2148 struct capability_mp_data mpc;
2149 struct capability_header *hdr;
d7c0a89a 2150 uint8_t action;
d62a17ae 2151 iana_afi_t pkt_afi;
2152 afi_t afi;
5c525538
RW
2153 iana_safi_t pkt_safi;
2154 safi_t safi;
d62a17ae 2155
2156 end = pnt + length;
2157
2158 while (pnt < end) {
2159 /* We need at least action, capability code and capability
2160 * length. */
2161 if (pnt + 3 > end) {
2162 zlog_info("%s Capability length error", peer->host);
0e35025e
DA
2163 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
2164 BGP_NOTIFY_SUBCODE_UNSPECIFIC);
d8151687 2165 return BGP_Stop;
d62a17ae 2166 }
2167 action = *pnt;
2168 hdr = (struct capability_header *)(pnt + 1);
2169
2170 /* Action value check. */
2171 if (action != CAPABILITY_ACTION_SET
2172 && action != CAPABILITY_ACTION_UNSET) {
2173 zlog_info("%s Capability Action Value error %d",
2174 peer->host, action);
0e35025e
DA
2175 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
2176 BGP_NOTIFY_SUBCODE_UNSPECIFIC);
d8151687 2177 return BGP_Stop;
d62a17ae 2178 }
2179
2180 if (bgp_debug_neighbor_events(peer))
2181 zlog_debug(
2182 "%s CAPABILITY has action: %d, code: %u, length %u",
2183 peer->host, action, hdr->code, hdr->length);
2184
2185 /* Capability length check. */
2186 if ((pnt + hdr->length + 3) > end) {
2187 zlog_info("%s Capability length error", peer->host);
0e35025e
DA
2188 bgp_notify_send(peer, BGP_NOTIFY_CEASE,
2189 BGP_NOTIFY_SUBCODE_UNSPECIFIC);
d8151687 2190 return BGP_Stop;
d62a17ae 2191 }
2192
2193 /* Fetch structure to the byte stream. */
2194 memcpy(&mpc, pnt + 3, sizeof(struct capability_mp_data));
d2b6417b 2195 pnt += hdr->length + 3;
d62a17ae 2196
2197 /* We know MP Capability Code. */
2198 if (hdr->code == CAPABILITY_CODE_MP) {
2199 pkt_afi = ntohs(mpc.afi);
2200 pkt_safi = mpc.safi;
2201
2202 /* Ignore capability when override-capability is set. */
2203 if (CHECK_FLAG(peer->flags,
2204 PEER_FLAG_OVERRIDE_CAPABILITY))
2205 continue;
2206
2207 /* Convert AFI, SAFI to internal values. */
2208 if (bgp_map_afi_safi_iana2int(pkt_afi, pkt_safi, &afi,
2209 &safi)) {
2210 if (bgp_debug_neighbor_events(peer))
2211 zlog_debug(
3efd0893 2212 "%s Dynamic Capability MP_EXT afi/safi invalid (%s/%s)",
748a041f
DS
2213 peer->host,
2214 iana_afi2str(pkt_afi),
2215 iana_safi2str(pkt_safi));
d62a17ae 2216 continue;
2217 }
2218
2219 /* Address family check. */
2220 if (bgp_debug_neighbor_events(peer))
2221 zlog_debug(
c386cdd8 2222 "%s CAPABILITY has %s MP_EXT CAP for afi/safi: %s/%s",
d62a17ae 2223 peer->host,
2224 action == CAPABILITY_ACTION_SET
2225 ? "Advertising"
2226 : "Removing",
c386cdd8
DA
2227 iana_afi2str(pkt_afi),
2228 iana_safi2str(pkt_safi));
d62a17ae 2229
2230 if (action == CAPABILITY_ACTION_SET) {
2231 peer->afc_recv[afi][safi] = 1;
2232 if (peer->afc[afi][safi]) {
2233 peer->afc_nego[afi][safi] = 1;
2234 bgp_announce_route(peer, afi, safi);
2235 }
2236 } else {
2237 peer->afc_recv[afi][safi] = 0;
2238 peer->afc_nego[afi][safi] = 0;
2239
2240 if (peer_active_nego(peer))
2241 bgp_clear_route(peer, afi, safi);
2242 else
d8151687 2243 return BGP_Stop;
d62a17ae 2244 }
2245 } else {
ade6974d 2246 flog_warn(
e50f7cfd 2247 EC_BGP_UNRECOGNIZED_CAPABILITY,
ade6974d
QY
2248 "%s unrecognized capability code: %d - ignored",
2249 peer->host, hdr->code);
d62a17ae 2250 }
d62a17ae 2251 }
d8151687
QY
2252
2253 /* No FSM action necessary */
2254 return BGP_PACKET_NOOP;
718e3744 2255}
2256
d8151687
QY
2257/**
2258 * Parse BGP CAPABILITY message for peer.
01b7ce2d 2259 *
d8151687
QY
2260 * Exported for unit testing.
2261 *
2262 * @param peer
2263 * @param size size of the packet
2264 * @return as in summary
01b7ce2d 2265 */
d62a17ae 2266int bgp_capability_receive(struct peer *peer, bgp_size_t size)
718e3744 2267{
d7c0a89a 2268 uint8_t *pnt;
d62a17ae 2269
2270 /* Fetch pointer. */
424ab01d 2271 pnt = stream_pnt(peer->curr);
d62a17ae 2272
2273 if (bgp_debug_neighbor_events(peer))
2274 zlog_debug("%s rcv CAPABILITY", peer->host);
2275
2276 /* If peer does not have the capability, send notification. */
2277 if (!CHECK_FLAG(peer->cap, PEER_CAP_DYNAMIC_ADV)) {
e50f7cfd 2278 flog_err(EC_BGP_NO_CAP,
1c50c1c0
QY
2279 "%s [Error] BGP dynamic capability is not enabled",
2280 peer->host);
d62a17ae 2281 bgp_notify_send(peer, BGP_NOTIFY_HEADER_ERR,
2282 BGP_NOTIFY_HEADER_BAD_MESTYPE);
d8151687 2283 return BGP_Stop;
d62a17ae 2284 }
2285
2286 /* Status must be Established. */
2287 if (peer->status != Established) {
af4c2728 2288 flog_err(
e50f7cfd 2289 EC_BGP_NO_CAP,
d62a17ae 2290 "%s [Error] Dynamic capability packet received under status %s",
2291 peer->host,
2292 lookup_msg(bgp_status_msg, peer->status, NULL));
0e35025e 2293 bgp_notify_send(peer, BGP_NOTIFY_FSM_ERR,
3893aeee 2294 bgp_fsm_error_subcode(peer->status));
d8151687 2295 return BGP_Stop;
d62a17ae 2296 }
2297
2298 /* Parse packet. */
2299 return bgp_capability_msg_parse(peer, pnt, size);
718e3744 2300}
6b0655a2 2301
d8151687
QY
2302/**
2303 * Processes a peer's input buffer.
2304 *
2305 * This function sidesteps the event loop and directly calls bgp_event_update()
2306 * after processing each BGP message. This is necessary to ensure proper
2307 * ordering of FSM events and unifies the behavior that was present previously,
2308 * whereby some of the packet handling functions would update the FSM and some
2309 * would not, making event flow difficult to understand. Please think twice
2310 * before hacking this.
2311 *
2312 * Thread type: THREAD_EVENT
2313 * @param thread
2314 * @return 0
2315 */
424ab01d 2316int bgp_process_packet(struct thread *thread)
718e3744 2317{
424ab01d 2318 /* Yes first of all get peer pointer. */
d8151687
QY
2319 struct peer *peer; // peer
2320 uint32_t rpkt_quanta_old; // how many packets to read
2321 int fsm_update_result; // return code of bgp_event_update()
2322 int mprc; // message processing return code
555e09d4 2323
424ab01d 2324 peer = THREAD_ARG(thread);
555e09d4
QY
2325 rpkt_quanta_old = atomic_load_explicit(&peer->bgp->rpkt_quanta,
2326 memory_order_relaxed);
e3c7270d 2327 fsm_update_result = 0;
555e09d4 2328
424ab01d 2329 /* Guard against scheduled events that occur after peer deletion. */
9eb217ff 2330 if (peer->status == Deleted || peer->status == Clearing)
d62a17ae 2331 return 0;
718e3744 2332
555e09d4 2333 unsigned int processed = 0;
d62a17ae 2334
555e09d4 2335 while (processed < rpkt_quanta_old) {
d7c0a89a 2336 uint8_t type = 0;
9eb217ff
QY
2337 bgp_size_t size;
2338 char notify_data_length[2];
d62a17ae 2339
00dffa8c 2340 frr_with_mutex(&peer->io_mtx) {
9eb217ff
QY
2341 peer->curr = stream_fifo_pop(peer->ibuf);
2342 }
d62a17ae 2343
9eb217ff
QY
2344 if (peer->curr == NULL) // no packets to process, hmm...
2345 return 0;
d62a17ae 2346
9eb217ff
QY
2347 /* skip the marker and copy the packet length */
2348 stream_forward_getp(peer->curr, BGP_MARKER_SIZE);
2349 memcpy(notify_data_length, stream_pnt(peer->curr), 2);
2350
2351 /* read in the packet length and type */
2352 size = stream_getw(peer->curr);
2353 type = stream_getc(peer->curr);
2354
584470fb 2355 hook_call(bgp_packet_dump, peer, type, size, peer->curr);
9eb217ff
QY
2356
2357 /* adjust size to exclude the marker + length + type */
2358 size -= BGP_HEADER_SIZE;
2359
2360 /* Read rest of the packet and call each sort of packet routine
2361 */
2362 switch (type) {
2363 case BGP_MSG_OPEN:
c7bb4f00 2364 frrtrace(2, frr_bgp, open_process, peer, size);
0112e9e0
QY
2365 atomic_fetch_add_explicit(&peer->open_in, 1,
2366 memory_order_relaxed);
d8151687
QY
2367 mprc = bgp_open_receive(peer, size);
2368 if (mprc == BGP_Stop)
af4c2728 2369 flog_err(
e50f7cfd 2370 EC_BGP_PKT_OPEN,
d8151687 2371 "%s: BGP OPEN receipt failed for peer: %s",
0767b4f3 2372 __func__, peer->host);
9eb217ff
QY
2373 break;
2374 case BGP_MSG_UPDATE:
c7bb4f00 2375 frrtrace(2, frr_bgp, update_process, peer, size);
0112e9e0
QY
2376 atomic_fetch_add_explicit(&peer->update_in, 1,
2377 memory_order_relaxed);
9eb217ff 2378 peer->readtime = monotime(NULL);
d8151687
QY
2379 mprc = bgp_update_receive(peer, size);
2380 if (mprc == BGP_Stop)
af4c2728 2381 flog_err(
e50f7cfd 2382 EC_BGP_UPDATE_RCV,
d8151687 2383 "%s: BGP UPDATE receipt failed for peer: %s",
0767b4f3 2384 __func__, peer->host);
9eb217ff
QY
2385 break;
2386 case BGP_MSG_NOTIFY:
c7bb4f00 2387 frrtrace(2, frr_bgp, notification_process, peer, size);
0112e9e0
QY
2388 atomic_fetch_add_explicit(&peer->notify_in, 1,
2389 memory_order_relaxed);
d8151687
QY
2390 mprc = bgp_notify_receive(peer, size);
2391 if (mprc == BGP_Stop)
af4c2728 2392 flog_err(
e50f7cfd 2393 EC_BGP_NOTIFY_RCV,
d8151687 2394 "%s: BGP NOTIFY receipt failed for peer: %s",
0767b4f3 2395 __func__, peer->host);
9eb217ff
QY
2396 break;
2397 case BGP_MSG_KEEPALIVE:
c7bb4f00 2398 frrtrace(2, frr_bgp, keepalive_process, peer, size);
9eb217ff 2399 peer->readtime = monotime(NULL);
0112e9e0
QY
2400 atomic_fetch_add_explicit(&peer->keepalive_in, 1,
2401 memory_order_relaxed);
d8151687
QY
2402 mprc = bgp_keepalive_receive(peer, size);
2403 if (mprc == BGP_Stop)
af4c2728 2404 flog_err(
e50f7cfd 2405 EC_BGP_KEEP_RCV,
d8151687 2406 "%s: BGP KEEPALIVE receipt failed for peer: %s",
0767b4f3 2407 __func__, peer->host);
9eb217ff
QY
2408 break;
2409 case BGP_MSG_ROUTE_REFRESH_NEW:
2410 case BGP_MSG_ROUTE_REFRESH_OLD:
c7bb4f00 2411 frrtrace(2, frr_bgp, refresh_process, peer, size);
0112e9e0
QY
2412 atomic_fetch_add_explicit(&peer->refresh_in, 1,
2413 memory_order_relaxed);
d8151687
QY
2414 mprc = bgp_route_refresh_receive(peer, size);
2415 if (mprc == BGP_Stop)
af4c2728 2416 flog_err(
e50f7cfd 2417 EC_BGP_RFSH_RCV,
d8151687 2418 "%s: BGP ROUTEREFRESH receipt failed for peer: %s",
0767b4f3 2419 __func__, peer->host);
9eb217ff
QY
2420 break;
2421 case BGP_MSG_CAPABILITY:
c7bb4f00 2422 frrtrace(2, frr_bgp, capability_process, peer, size);
0112e9e0
QY
2423 atomic_fetch_add_explicit(&peer->dynamic_cap_in, 1,
2424 memory_order_relaxed);
d8151687
QY
2425 mprc = bgp_capability_receive(peer, size);
2426 if (mprc == BGP_Stop)
af4c2728 2427 flog_err(
e50f7cfd 2428 EC_BGP_CAP_RCV,
d8151687 2429 "%s: BGP CAPABILITY receipt failed for peer: %s",
0767b4f3 2430 __func__, peer->host);
9eb217ff 2431 break;
e3c7270d 2432 default:
db878db0
QY
2433 /* Suppress uninitialized variable warning */
2434 mprc = 0;
5041dc4f 2435 (void)mprc;
becedef6
QY
2436 /*
2437 * The message type should have been sanitized before
2438 * we ever got here. Receipt of a message with an
2439 * invalid header at this point is indicative of a
2440 * security issue.
2441 */
e3c7270d 2442 assert (!"Message of invalid type received during input processing");
9eb217ff
QY
2443 }
2444
d8151687
QY
2445 /* delete processed packet */
2446 stream_free(peer->curr);
2447 peer->curr = NULL;
2448 processed++;
9eb217ff 2449
d8151687
QY
2450 /* Update FSM */
2451 if (mprc != BGP_PACKET_NOOP)
2452 fsm_update_result = bgp_event_update(peer, mprc);
e3c7270d
QY
2453 else
2454 continue;
d8151687 2455
becedef6
QY
2456 /*
2457 * If peer was deleted, do not process any more packets. This
2458 * is usually due to executing BGP_Stop or a stub deletion.
2459 */
d8151687
QY
2460 if (fsm_update_result == FSM_PEER_TRANSFERRED
2461 || fsm_update_result == FSM_PEER_STOPPED)
2462 break;
d62a17ae 2463 }
2464
d8151687
QY
2465 if (fsm_update_result != FSM_PEER_TRANSFERRED
2466 && fsm_update_result != FSM_PEER_STOPPED) {
00dffa8c 2467 frr_with_mutex(&peer->io_mtx) {
becedef6
QY
2468 // more work to do, come back later
2469 if (peer->ibuf->count > 0)
4af76660
QY
2470 thread_add_timer_msec(
2471 bm->master, bgp_process_packet, peer, 0,
2472 &peer->t_process_packet);
d8151687 2473 }
718e3744 2474 }
2475
d62a17ae 2476 return 0;
718e3744 2477}
9e3b51a7 2478
2479/* Send EOR when routes are processed by selection deferral timer */
2480void bgp_send_delayed_eor(struct bgp *bgp)
2481{
2482 struct peer *peer;
2483 struct listnode *node, *nnode;
2484
2485 /* EOR message sent in bgp_write_proceed_actions */
2486 for (ALL_LIST_ELEMENTS(bgp->peer, node, nnode, peer))
2487 bgp_write_proceed_actions(peer);
2488}