blob: 201ffbbe5577122fdf6b7e6290a713da28821886 [file] [log] [blame]
paul718e3742002-12-13 20:15:29 +00001/* BGP packet management routine.
2 Copyright (C) 1999 Kunihiro Ishiguro
3
4This file is part of GNU Zebra.
5
6GNU Zebra is free software; you can redistribute it and/or modify it
7under the terms of the GNU General Public License as published by the
8Free Software Foundation; either version 2, or (at your option) any
9later version.
10
11GNU Zebra is distributed in the hope that it will be useful, but
12WITHOUT ANY WARRANTY; without even the implied warranty of
13MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14General Public License for more details.
15
16You should have received a copy of the GNU General Public License
17along with GNU Zebra; see the file COPYING. If not, write to the Free
18Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
1902111-1307, USA. */
20
21#include <zebra.h>
22
23#include "thread.h"
24#include "stream.h"
25#include "network.h"
26#include "prefix.h"
27#include "command.h"
28#include "log.h"
29#include "memory.h"
30#include "sockunion.h" /* for inet_ntop () */
31#include "linklist.h"
32#include "plist.h"
33
34#include "bgpd/bgpd.h"
35#include "bgpd/bgp_table.h"
36#include "bgpd/bgp_dump.h"
37#include "bgpd/bgp_attr.h"
38#include "bgpd/bgp_debug.h"
39#include "bgpd/bgp_fsm.h"
40#include "bgpd/bgp_route.h"
41#include "bgpd/bgp_packet.h"
42#include "bgpd/bgp_open.h"
43#include "bgpd/bgp_aspath.h"
44#include "bgpd/bgp_community.h"
45#include "bgpd/bgp_ecommunity.h"
46#include "bgpd/bgp_network.h"
47#include "bgpd/bgp_mplsvpn.h"
48#include "bgpd/bgp_advertise.h"
hasso93406d82005-02-02 14:40:33 +000049#include "bgpd/bgp_vty.h"
paul718e3742002-12-13 20:15:29 +000050
51int stream_put_prefix (struct stream *, struct prefix *);
52
53/* Set up BGP packet marker and packet type. */
54static int
55bgp_packet_set_marker (struct stream *s, u_char type)
56{
57 int i;
58
59 /* Fill in marker. */
60 for (i = 0; i < BGP_MARKER_SIZE; i++)
61 stream_putc (s, 0xff);
62
63 /* Dummy total length. This field is should be filled in later on. */
64 stream_putw (s, 0);
65
66 /* BGP packet type. */
67 stream_putc (s, type);
68
69 /* Return current stream size. */
70 return stream_get_putp (s);
71}
72
73/* Set BGP packet header size entry. If size is zero then use current
74 stream size. */
75static int
76bgp_packet_set_size (struct stream *s)
77{
78 int cp;
79
80 /* Preserve current pointer. */
81 cp = stream_get_putp (s);
82 stream_set_putp (s, BGP_MARKER_SIZE);
83 stream_putw (s, cp);
84
85 /* Write back current pointer. */
86 stream_set_putp (s, cp);
87
88 return cp;
89}
90
91/* Add new packet to the peer. */
92void
93bgp_packet_add (struct peer *peer, struct stream *s)
94{
95 /* Add packet to the end of list. */
96 stream_fifo_push (peer->obuf, s);
97}
98
99/* Free first packet. */
100void
101bgp_packet_delete (struct peer *peer)
102{
103 stream_free (stream_fifo_pop (peer->obuf));
104}
105
106/* Duplicate packet. */
107struct stream *
108bgp_packet_dup (struct stream *s)
109{
110 struct stream *new;
111
112 new = stream_new (stream_get_endp (s));
113
114 new->endp = s->endp;
115 new->putp = s->putp;
116 new->getp = s->getp;
117
118 memcpy (new->data, s->data, stream_get_endp (s));
119
120 return new;
121}
122
123/* Check file descriptor whether connect is established. */
124static void
125bgp_connect_check (struct peer *peer)
126{
127 int status;
paul5228ad22004-06-04 17:58:18 +0000128 socklen_t slen;
paul718e3742002-12-13 20:15:29 +0000129 int ret;
130
131 /* Anyway I have to reset read and write thread. */
132 BGP_READ_OFF (peer->t_read);
133 BGP_WRITE_OFF (peer->t_write);
134
135 /* Check file descriptor. */
136 slen = sizeof (status);
pauleb821182004-05-01 08:44:08 +0000137 ret = getsockopt(peer->fd, SOL_SOCKET, SO_ERROR, (void *) &status, &slen);
paul718e3742002-12-13 20:15:29 +0000138
139 /* If getsockopt is fail, this is fatal error. */
140 if (ret < 0)
141 {
142 zlog (peer->log, LOG_INFO, "can't get sockopt for nonblocking connect");
143 BGP_EVENT_ADD (peer, TCP_fatal_error);
144 return;
145 }
146
147 /* When status is 0 then TCP connection is established. */
148 if (status == 0)
149 {
150 BGP_EVENT_ADD (peer, TCP_connection_open);
151 }
152 else
153 {
154 if (BGP_DEBUG (events, EVENTS))
ajs6b514742004-12-08 21:03:23 +0000155 plog_debug (peer->log, "%s [Event] Connect failed (%s)",
ajs6099b3b2004-11-20 02:06:59 +0000156 peer->host, safe_strerror (errno));
paul718e3742002-12-13 20:15:29 +0000157 BGP_EVENT_ADD (peer, TCP_connection_open_failed);
158 }
159}
160
161/* Make BGP update packet. */
162struct stream *
163bgp_update_packet (struct peer *peer, afi_t afi, safi_t safi)
164{
165 struct stream *s;
166 struct bgp_adj_out *adj;
167 struct bgp_advertise *adv;
168 struct stream *packet;
169 struct bgp_node *rn = NULL;
170 struct bgp_info *binfo = NULL;
171 bgp_size_t total_attr_len = 0;
172 unsigned long pos;
173 char buf[BUFSIZ];
174 struct prefix_rd *prd = NULL;
175 char *tag = NULL;
176
177 s = peer->work;
178 stream_reset (s);
179
180 adv = FIFO_HEAD (&peer->sync[afi][safi]->update);
181
182 while (adv)
183 {
184 if (adv->rn)
185 rn = adv->rn;
186 adj = adv->adj;
187 if (adv->binfo)
188 binfo = adv->binfo;
189#ifdef MPLS_VPN
190 if (rn)
191 prd = (struct prefix_rd *) &rn->prn->p;
192 if (binfo)
193 tag = binfo->tag;
194#endif /* MPLS_VPN */
195
196 /* When remaining space can't include NLRI and it's length. */
197 if (rn && STREAM_REMAIN (s) <= BGP_NLRI_LENGTH + PSIZE (rn->p.prefixlen))
198 break;
199
200 /* If packet is empty, set attribute. */
201 if (stream_empty (s))
202 {
203 bgp_packet_set_marker (s, BGP_MSG_UPDATE);
204 stream_putw (s, 0);
205 pos = stream_get_putp (s);
206 stream_putw (s, 0);
paul5228ad22004-06-04 17:58:18 +0000207 total_attr_len = bgp_packet_attribute (NULL, peer, s,
208 adv->baa->attr,
209 &rn->p, afi, safi,
210 binfo->peer, prd, tag);
paul718e3742002-12-13 20:15:29 +0000211 stream_putw_at (s, pos, total_attr_len);
212 }
213
214 if (afi == AFI_IP && safi == SAFI_UNICAST)
215 stream_put_prefix (s, &rn->p);
216
217 if (BGP_DEBUG (update, UPDATE_OUT))
ajs6b514742004-12-08 21:03:23 +0000218 zlog (peer->log, LOG_DEBUG, "%s send UPDATE %s/%d",
paul718e3742002-12-13 20:15:29 +0000219 peer->host,
220 inet_ntop (rn->p.family, &(rn->p.u.prefix), buf, BUFSIZ),
221 rn->p.prefixlen);
222
223 /* Synchnorize attribute. */
224 if (adj->attr)
225 bgp_attr_unintern (adj->attr);
226 else
227 peer->scount[afi][safi]++;
228
229 adj->attr = bgp_attr_intern (adv->baa->attr);
230
231 adv = bgp_advertise_clean (peer, adj, afi, safi);
232
233 if (! (afi == AFI_IP && safi == SAFI_UNICAST))
234 break;
235 }
236
237 if (! stream_empty (s))
238 {
239 bgp_packet_set_size (s);
240 packet = bgp_packet_dup (s);
241 bgp_packet_add (peer, packet);
pauleb821182004-05-01 08:44:08 +0000242 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +0000243 stream_reset (s);
244 return packet;
245 }
246 return NULL;
hasso93406d82005-02-02 14:40:33 +0000247}
paul718e3742002-12-13 20:15:29 +0000248
hasso93406d82005-02-02 14:40:33 +0000249struct stream *
250bgp_update_packet_eor (struct peer *peer, afi_t afi, safi_t safi)
251{
252 struct stream *s;
253 struct stream *packet;
254
255#ifdef DISABLE_BGP_ANNOUNCE
256 return;
257#endif /* DISABLE_BGP_ANNOUNCE */
258
259 if (BGP_DEBUG (normal, NORMAL))
260 zlog_debug ("send End-of-RIB for %s to %s", afi_safi_print (afi, safi), peer->host);
261
262 s = stream_new (BGP_MAX_PACKET_SIZE);
263
264 /* Make BGP update packet. */
265 bgp_packet_set_marker (s, BGP_MSG_UPDATE);
266
267 /* Unfeasible Routes Length */
268 stream_putw (s, 0);
269
270 if (afi == AFI_IP && safi == SAFI_UNICAST)
271 {
272 /* Total Path Attribute Length */
273 stream_putw (s, 0);
274 }
275 else
276 {
277 /* Total Path Attribute Length */
278 stream_putw (s, 6);
279 stream_putc (s, BGP_ATTR_FLAG_OPTIONAL);
280 stream_putc (s, BGP_ATTR_MP_UNREACH_NLRI);
281 stream_putc (s, 3);
282 stream_putw (s, afi);
283 stream_putc (s, safi);
284 }
285
286 bgp_packet_set_size (s);
287 packet = bgp_packet_dup (s);
288 bgp_packet_add (peer, packet);
289 stream_free (s);
290 return packet;
paul718e3742002-12-13 20:15:29 +0000291}
292
293/* Make BGP withdraw packet. */
294struct stream *
295bgp_withdraw_packet (struct peer *peer, afi_t afi, safi_t safi)
296{
297 struct stream *s;
298 struct stream *packet;
299 struct bgp_adj_out *adj;
300 struct bgp_advertise *adv;
301 struct bgp_node *rn;
302 unsigned long pos;
303 bgp_size_t unfeasible_len;
304 bgp_size_t total_attr_len;
305 char buf[BUFSIZ];
306 struct prefix_rd *prd = NULL;
307
308 s = peer->work;
309 stream_reset (s);
310
311 while ((adv = FIFO_HEAD (&peer->sync[afi][safi]->withdraw)) != NULL)
312 {
313 adj = adv->adj;
314 rn = adv->rn;
315#ifdef MPLS_VPN
316 prd = (struct prefix_rd *) &rn->prn->p;
317#endif /* MPLS_VPN */
318
319 if (STREAM_REMAIN (s)
hasso4372df72004-05-20 10:20:02 +0000320 < (BGP_NLRI_LENGTH + BGP_TOTAL_ATTR_LEN + PSIZE (rn->p.prefixlen)))
paul718e3742002-12-13 20:15:29 +0000321 break;
322
323 if (stream_empty (s))
324 {
325 bgp_packet_set_marker (s, BGP_MSG_UPDATE);
326 stream_putw (s, 0);
327 }
328
329 if (afi == AFI_IP && safi == SAFI_UNICAST)
330 stream_put_prefix (s, &rn->p);
331 else
332 {
333 pos = stream_get_putp (s);
334 stream_putw (s, 0);
335 total_attr_len
336 = bgp_packet_withdraw (peer, s, &rn->p, afi, safi, prd, NULL);
337
338 /* Set total path attribute length. */
339 stream_putw_at (s, pos, total_attr_len);
340 }
341
342 if (BGP_DEBUG (update, UPDATE_OUT))
ajs6b514742004-12-08 21:03:23 +0000343 zlog (peer->log, LOG_DEBUG, "%s send UPDATE %s/%d -- unreachable",
paul718e3742002-12-13 20:15:29 +0000344 peer->host,
345 inet_ntop (rn->p.family, &(rn->p.u.prefix), buf, BUFSIZ),
346 rn->p.prefixlen);
347
348 peer->scount[afi][safi]--;
349
350 bgp_adj_out_remove (rn, adj, peer, afi, safi);
351 bgp_unlock_node (rn);
352
353 if (! (afi == AFI_IP && safi == SAFI_UNICAST))
354 break;
355 }
356
357 if (! stream_empty (s))
358 {
359 if (afi == AFI_IP && safi == SAFI_UNICAST)
360 {
361 unfeasible_len
362 = stream_get_putp (s) - BGP_HEADER_SIZE - BGP_UNFEASIBLE_LEN;
363 stream_putw_at (s, BGP_HEADER_SIZE, unfeasible_len);
364 stream_putw (s, 0);
365 }
366 bgp_packet_set_size (s);
367 packet = bgp_packet_dup (s);
368 bgp_packet_add (peer, packet);
369 stream_reset (s);
370 return packet;
371 }
372
373 return NULL;
374}
375
376void
377bgp_default_update_send (struct peer *peer, struct attr *attr,
378 afi_t afi, safi_t safi, struct peer *from)
379{
380 struct stream *s;
381 struct stream *packet;
382 struct prefix p;
383 unsigned long pos;
384 bgp_size_t total_attr_len;
385 char attrstr[BUFSIZ];
386 char buf[BUFSIZ];
387
388#ifdef DISABLE_BGP_ANNOUNCE
389 return;
390#endif /* DISABLE_BGP_ANNOUNCE */
391
392 if (afi == AFI_IP)
393 str2prefix ("0.0.0.0/0", &p);
394#ifdef HAVE_IPV6
395 else
396 str2prefix ("::/0", &p);
397#endif /* HAVE_IPV6 */
398
399 /* Logging the attribute. */
400 if (BGP_DEBUG (update, UPDATE_OUT))
401 {
402 bgp_dump_attr (peer, attr, attrstr, BUFSIZ);
ajs6b514742004-12-08 21:03:23 +0000403 zlog (peer->log, LOG_DEBUG, "%s send UPDATE %s/%d %s",
paul718e3742002-12-13 20:15:29 +0000404 peer->host, inet_ntop(p.family, &(p.u.prefix), buf, BUFSIZ),
405 p.prefixlen, attrstr);
406 }
407
408 s = stream_new (BGP_MAX_PACKET_SIZE);
409
410 /* Make BGP update packet. */
411 bgp_packet_set_marker (s, BGP_MSG_UPDATE);
412
413 /* Unfeasible Routes Length. */
414 stream_putw (s, 0);
415
416 /* Make place for total attribute length. */
417 pos = stream_get_putp (s);
418 stream_putw (s, 0);
419 total_attr_len = bgp_packet_attribute (NULL, peer, s, attr, &p, afi, safi, from, NULL, NULL);
420
421 /* Set Total Path Attribute Length. */
422 stream_putw_at (s, pos, total_attr_len);
423
424 /* NLRI set. */
425 if (p.family == AF_INET && safi == SAFI_UNICAST)
426 stream_put_prefix (s, &p);
427
428 /* Set size. */
429 bgp_packet_set_size (s);
430
431 packet = bgp_packet_dup (s);
432 stream_free (s);
433
434 /* Dump packet if debug option is set. */
435#ifdef DEBUG
436 bgp_packet_dump (packet);
437#endif /* DEBUG */
438
439 /* Add packet to the peer. */
440 bgp_packet_add (peer, packet);
441
pauleb821182004-05-01 08:44:08 +0000442 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +0000443}
444
445void
446bgp_default_withdraw_send (struct peer *peer, afi_t afi, safi_t safi)
447{
448 struct stream *s;
449 struct stream *packet;
450 struct prefix p;
451 unsigned long pos;
452 unsigned long cp;
453 bgp_size_t unfeasible_len;
454 bgp_size_t total_attr_len;
455 char buf[BUFSIZ];
456
457#ifdef DISABLE_BGP_ANNOUNCE
458 return;
459#endif /* DISABLE_BGP_ANNOUNCE */
460
461 if (afi == AFI_IP)
462 str2prefix ("0.0.0.0/0", &p);
463#ifdef HAVE_IPV6
464 else
465 str2prefix ("::/0", &p);
466#endif /* HAVE_IPV6 */
467
468 total_attr_len = 0;
469 pos = 0;
470
471 if (BGP_DEBUG (update, UPDATE_OUT))
ajs6b514742004-12-08 21:03:23 +0000472 zlog (peer->log, LOG_DEBUG, "%s send UPDATE %s/%d -- unreachable",
paul718e3742002-12-13 20:15:29 +0000473 peer->host, inet_ntop(p.family, &(p.u.prefix), buf, BUFSIZ),
474 p.prefixlen);
475
476 s = stream_new (BGP_MAX_PACKET_SIZE);
477
478 /* Make BGP update packet. */
479 bgp_packet_set_marker (s, BGP_MSG_UPDATE);
480
481 /* Unfeasible Routes Length. */;
482 cp = stream_get_putp (s);
483 stream_putw (s, 0);
484
485 /* Withdrawn Routes. */
486 if (p.family == AF_INET && safi == SAFI_UNICAST)
487 {
488 stream_put_prefix (s, &p);
489
490 unfeasible_len = stream_get_putp (s) - cp - 2;
491
492 /* Set unfeasible len. */
493 stream_putw_at (s, cp, unfeasible_len);
494
495 /* Set total path attribute length. */
496 stream_putw (s, 0);
497 }
498 else
499 {
500 pos = stream_get_putp (s);
501 stream_putw (s, 0);
502 total_attr_len = bgp_packet_withdraw (peer, s, &p, afi, safi, NULL, NULL);
503
504 /* Set total path attribute length. */
505 stream_putw_at (s, pos, total_attr_len);
506 }
507
508 bgp_packet_set_size (s);
509
510 packet = bgp_packet_dup (s);
511 stream_free (s);
512
513 /* Add packet to the peer. */
514 bgp_packet_add (peer, packet);
515
pauleb821182004-05-01 08:44:08 +0000516 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +0000517}
518
519/* Get next packet to be written. */
520struct stream *
521bgp_write_packet (struct peer *peer)
522{
523 afi_t afi;
524 safi_t safi;
525 struct stream *s = NULL;
526 struct bgp_advertise *adv;
527
528 s = stream_fifo_head (peer->obuf);
529 if (s)
530 return s;
531
532 for (afi = AFI_IP; afi < AFI_MAX; afi++)
533 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
534 {
535 adv = FIFO_HEAD (&peer->sync[afi][safi]->withdraw);
536 if (adv)
537 {
538 s = bgp_withdraw_packet (peer, afi, safi);
539 if (s)
540 return s;
541 }
542 }
543
544 for (afi = AFI_IP; afi < AFI_MAX; afi++)
545 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
546 {
547 adv = FIFO_HEAD (&peer->sync[afi][safi]->update);
548 if (adv)
549 {
550 if (adv->binfo && adv->binfo->uptime < peer->synctime)
hasso93406d82005-02-02 14:40:33 +0000551 {
552 if (CHECK_FLAG (adv->binfo->peer->cap, PEER_CAP_RESTART_RCV)
553 && CHECK_FLAG (adv->binfo->peer->cap, PEER_CAP_RESTART_ADV)
554 && ! CHECK_FLAG (adv->binfo->flags, BGP_INFO_STALE)
555 && safi != SAFI_MPLS_VPN)
556 {
557 if (CHECK_FLAG (adv->binfo->peer->af_sflags[afi][safi],
558 PEER_STATUS_EOR_RECEIVED))
559 s = bgp_update_packet (peer, afi, safi);
560 }
561 else
562 s = bgp_update_packet (peer, afi, safi);
563 }
paul718e3742002-12-13 20:15:29 +0000564
565 if (s)
566 return s;
567 }
hasso93406d82005-02-02 14:40:33 +0000568
569 if (CHECK_FLAG (peer->cap, PEER_CAP_RESTART_RCV))
570 {
571 if (peer->afc_nego[afi][safi] && peer->synctime
572 && ! CHECK_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_EOR_SEND)
573 && safi != SAFI_MPLS_VPN)
574 {
575 SET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_EOR_SEND);
576 return bgp_update_packet_eor (peer, afi, safi);
577 }
578 }
paul718e3742002-12-13 20:15:29 +0000579 }
580
581 return NULL;
582}
583
584/* Is there partially written packet or updates we can send right
585 now. */
586int
587bgp_write_proceed (struct peer *peer)
588{
589 afi_t afi;
590 safi_t safi;
591 struct bgp_advertise *adv;
592
593 if (stream_fifo_head (peer->obuf))
594 return 1;
595
596 for (afi = AFI_IP; afi < AFI_MAX; afi++)
597 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
598 if (FIFO_HEAD (&peer->sync[afi][safi]->withdraw))
599 return 1;
600
601 for (afi = AFI_IP; afi < AFI_MAX; afi++)
602 for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
603 if ((adv = FIFO_HEAD (&peer->sync[afi][safi]->update)) != NULL)
604 if (adv->binfo->uptime < peer->synctime)
605 return 1;
606
607 return 0;
608}
609
610/* Write packet to the peer. */
611int
612bgp_write (struct thread *thread)
613{
614 struct peer *peer;
615 u_char type;
616 struct stream *s;
617 int num;
paulfd79ac92004-10-13 05:06:08 +0000618 unsigned int count = 0;
paul718e3742002-12-13 20:15:29 +0000619 int write_errno;
620
621 /* Yes first of all get peer pointer. */
622 peer = THREAD_ARG (thread);
623 peer->t_write = NULL;
624
625 /* For non-blocking IO check. */
626 if (peer->status == Connect)
627 {
628 bgp_connect_check (peer);
629 return 0;
630 }
631
632 /* Nonblocking write until TCP output buffer is full. */
633 while (1)
634 {
635 int writenum;
paula24a7e12005-01-05 08:14:13 +0000636 int val;
paul718e3742002-12-13 20:15:29 +0000637
638 s = bgp_write_packet (peer);
639 if (! s)
640 return 0;
paula24a7e12005-01-05 08:14:13 +0000641
642 /* XXX: FIXME, the socket should be NONBLOCK from the start
643 * status shouldnt need to be toggled on each write
644 */
645 val = fcntl (peer->fd, F_GETFL, 0);
646 fcntl (peer->fd, F_SETFL, val|O_NONBLOCK);
paul718e3742002-12-13 20:15:29 +0000647
648 /* Number of bytes to be sent. */
649 writenum = stream_get_endp (s) - stream_get_getp (s);
650
651 /* Call write() system call. */
pauleb821182004-05-01 08:44:08 +0000652 num = write (peer->fd, STREAM_PNT (s), writenum);
paul718e3742002-12-13 20:15:29 +0000653 write_errno = errno;
paula24a7e12005-01-05 08:14:13 +0000654 fcntl (peer->fd, F_SETFL, val);
paul718e3742002-12-13 20:15:29 +0000655 if (num <= 0)
656 {
657 /* Partial write. */
658 if (write_errno == EWOULDBLOCK || write_errno == EAGAIN)
659 break;
660
661 bgp_stop (peer);
662 peer->status = Idle;
663 bgp_timer_set (peer);
664 return 0;
665 }
666 if (num != writenum)
667 {
668 stream_forward (s, num);
669
670 if (write_errno == EAGAIN)
671 break;
672
673 continue;
674 }
675
676 /* Retrieve BGP packet type. */
677 stream_set_getp (s, BGP_MARKER_SIZE + 2);
678 type = stream_getc (s);
679
680 switch (type)
681 {
682 case BGP_MSG_OPEN:
683 peer->open_out++;
684 break;
685 case BGP_MSG_UPDATE:
686 peer->update_out++;
687 break;
688 case BGP_MSG_NOTIFY:
689 peer->notify_out++;
690 /* Double start timer. */
691 peer->v_start *= 2;
692
693 /* Overflow check. */
694 if (peer->v_start >= (60 * 2))
695 peer->v_start = (60 * 2);
696
697 /* BGP_EVENT_ADD (peer, BGP_Stop); */
698 bgp_stop (peer);
699 peer->status = Idle;
700 bgp_timer_set (peer);
701 return 0;
702 break;
703 case BGP_MSG_KEEPALIVE:
704 peer->keepalive_out++;
705 break;
706 case BGP_MSG_ROUTE_REFRESH_NEW:
707 case BGP_MSG_ROUTE_REFRESH_OLD:
708 peer->refresh_out++;
709 break;
710 case BGP_MSG_CAPABILITY:
711 peer->dynamic_cap_out++;
712 break;
713 }
714
715 /* OK we send packet so delete it. */
716 bgp_packet_delete (peer);
717
718 if (++count >= BGP_WRITE_PACKET_MAX)
719 break;
720 }
721
722 if (bgp_write_proceed (peer))
pauleb821182004-05-01 08:44:08 +0000723 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +0000724
725 return 0;
726}
727
728/* This is only for sending NOTIFICATION message to neighbor. */
729int
730bgp_write_notify (struct peer *peer)
731{
732 int ret;
733 u_char type;
734 struct stream *s;
735
736 /* There should be at least one packet. */
737 s = stream_fifo_head (peer->obuf);
738 if (!s)
739 return 0;
740 assert (stream_get_endp (s) >= BGP_HEADER_SIZE);
741
742 /* I'm not sure fd is writable. */
pauleb821182004-05-01 08:44:08 +0000743 ret = writen (peer->fd, STREAM_DATA (s), stream_get_endp (s));
paul718e3742002-12-13 20:15:29 +0000744 if (ret <= 0)
745 {
746 bgp_stop (peer);
747 peer->status = Idle;
748 bgp_timer_set (peer);
749 return 0;
750 }
751
752 /* Retrieve BGP packet type. */
753 stream_set_getp (s, BGP_MARKER_SIZE + 2);
754 type = stream_getc (s);
755
756 assert (type == BGP_MSG_NOTIFY);
757
758 /* Type should be notify. */
759 peer->notify_out++;
760
761 /* Double start timer. */
762 peer->v_start *= 2;
763
764 /* Overflow check. */
765 if (peer->v_start >= (60 * 2))
766 peer->v_start = (60 * 2);
767
768 /* We don't call event manager at here for avoiding other events. */
769 bgp_stop (peer);
770 peer->status = Idle;
771 bgp_timer_set (peer);
772
773 return 0;
774}
775
776/* Make keepalive packet and send it to the peer. */
777void
778bgp_keepalive_send (struct peer *peer)
779{
780 struct stream *s;
781 int length;
782
783 s = stream_new (BGP_MAX_PACKET_SIZE);
784
785 /* Make keepalive packet. */
786 bgp_packet_set_marker (s, BGP_MSG_KEEPALIVE);
787
788 /* Set packet size. */
789 length = bgp_packet_set_size (s);
790
791 /* Dump packet if debug option is set. */
792 /* bgp_packet_dump (s); */
793
794 if (BGP_DEBUG (keepalive, KEEPALIVE))
ajs6b514742004-12-08 21:03:23 +0000795 zlog_debug ("%s sending KEEPALIVE", peer->host);
paul718e3742002-12-13 20:15:29 +0000796 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +0000797 zlog_debug ("%s send message type %d, length (incl. header) %d",
paul718e3742002-12-13 20:15:29 +0000798 peer->host, BGP_MSG_KEEPALIVE, length);
799
800 /* Add packet to the peer. */
801 bgp_packet_add (peer, s);
802
pauleb821182004-05-01 08:44:08 +0000803 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +0000804}
805
806/* Make open packet and send it to the peer. */
807void
808bgp_open_send (struct peer *peer)
809{
810 struct stream *s;
811 int length;
812 u_int16_t send_holdtime;
813 as_t local_as;
814
815 if (CHECK_FLAG (peer->config, PEER_CONFIG_TIMER))
816 send_holdtime = peer->holdtime;
817 else
818 send_holdtime = peer->bgp->default_holdtime;
819
820 /* local-as Change */
821 if (peer->change_local_as)
822 local_as = peer->change_local_as;
823 else
824 local_as = peer->local_as;
825
826 s = stream_new (BGP_MAX_PACKET_SIZE);
827
828 /* Make open packet. */
829 bgp_packet_set_marker (s, BGP_MSG_OPEN);
830
831 /* Set open packet values. */
832 stream_putc (s, BGP_VERSION_4); /* BGP version */
833 stream_putw (s, local_as); /* My Autonomous System*/
834 stream_putw (s, send_holdtime); /* Hold Time */
835 stream_put_in_addr (s, &peer->local_id); /* BGP Identifier */
836
837 /* Set capability code. */
838 bgp_open_capability (s, peer);
839
840 /* Set BGP packet length. */
841 length = bgp_packet_set_size (s);
842
843 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +0000844 zlog_debug ("%s sending OPEN, version %d, my as %d, holdtime %d, id %s",
paul718e3742002-12-13 20:15:29 +0000845 peer->host, BGP_VERSION_4, local_as,
846 send_holdtime, inet_ntoa (peer->local_id));
847
848 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +0000849 zlog_debug ("%s send message type %d, length (incl. header) %d",
paul718e3742002-12-13 20:15:29 +0000850 peer->host, BGP_MSG_OPEN, length);
851
852 /* Dump packet if debug option is set. */
853 /* bgp_packet_dump (s); */
854
855 /* Add packet to the peer. */
856 bgp_packet_add (peer, s);
857
pauleb821182004-05-01 08:44:08 +0000858 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +0000859}
860
861/* Send BGP notify packet with data potion. */
862void
863bgp_notify_send_with_data (struct peer *peer, u_char code, u_char sub_code,
864 u_char *data, size_t datalen)
865{
866 struct stream *s;
867 int length;
868
869 /* Allocate new stream. */
870 s = stream_new (BGP_MAX_PACKET_SIZE);
871
872 /* Make nitify packet. */
873 bgp_packet_set_marker (s, BGP_MSG_NOTIFY);
874
875 /* Set notify packet values. */
876 stream_putc (s, code); /* BGP notify code */
877 stream_putc (s, sub_code); /* BGP notify sub_code */
878
879 /* If notify data is present. */
880 if (data)
881 stream_write (s, data, datalen);
882
883 /* Set BGP packet length. */
884 length = bgp_packet_set_size (s);
885
886 /* Add packet to the peer. */
887 stream_fifo_clean (peer->obuf);
888 bgp_packet_add (peer, s);
889
890 /* For debug */
891 {
892 struct bgp_notify bgp_notify;
893 int first = 0;
894 int i;
895 char c[4];
896
897 bgp_notify.code = code;
898 bgp_notify.subcode = sub_code;
899 bgp_notify.data = NULL;
900 bgp_notify.length = length - BGP_MSG_NOTIFY_MIN_SIZE;
901
902 if (bgp_notify.length)
903 {
904 bgp_notify.data = XMALLOC (MTYPE_TMP, bgp_notify.length * 3);
905 for (i = 0; i < bgp_notify.length; i++)
906 if (first)
907 {
908 sprintf (c, " %02x", data[i]);
909 strcat (bgp_notify.data, c);
910 }
911 else
912 {
913 first = 1;
914 sprintf (c, "%02x", data[i]);
915 strcpy (bgp_notify.data, c);
916 }
917 }
918 bgp_notify_print (peer, &bgp_notify, "sending");
919 if (bgp_notify.data)
920 XFREE (MTYPE_TMP, bgp_notify.data);
921 }
922
923 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +0000924 zlog_debug ("%s send message type %d, length (incl. header) %d",
paul718e3742002-12-13 20:15:29 +0000925 peer->host, BGP_MSG_NOTIFY, length);
926
hassoe0701b72004-05-20 09:19:34 +0000927 /* peer reset cause */
928 if (sub_code != BGP_NOTIFY_CEASE_CONFIG_CHANGE)
929 {
930 if (sub_code == BGP_NOTIFY_CEASE_ADMIN_RESET)
931 peer->last_reset = PEER_DOWN_USER_RESET;
932 else if (sub_code == BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN)
933 peer->last_reset = PEER_DOWN_USER_SHUTDOWN;
934 else
935 peer->last_reset = PEER_DOWN_NOTIFY_SEND;
936 }
937
paul718e3742002-12-13 20:15:29 +0000938 /* Call imidiately. */
939 BGP_WRITE_OFF (peer->t_write);
940
941 bgp_write_notify (peer);
942}
943
944/* Send BGP notify packet. */
945void
946bgp_notify_send (struct peer *peer, u_char code, u_char sub_code)
947{
948 bgp_notify_send_with_data (peer, code, sub_code, NULL, 0);
949}
950
paulfd79ac92004-10-13 05:06:08 +0000951const char *
paul718e3742002-12-13 20:15:29 +0000952afi2str (afi_t afi)
953{
954 if (afi == AFI_IP)
955 return "AFI_IP";
956 else if (afi == AFI_IP6)
957 return "AFI_IP6";
958 else
959 return "Unknown AFI";
960}
961
paulfd79ac92004-10-13 05:06:08 +0000962const char *
paul718e3742002-12-13 20:15:29 +0000963safi2str (safi_t safi)
964{
965 if (safi == SAFI_UNICAST)
966 return "SAFI_UNICAST";
967 else if (safi == SAFI_MULTICAST)
968 return "SAFI_MULTICAST";
969 else if (safi == SAFI_MPLS_VPN || safi == BGP_SAFI_VPNV4)
970 return "SAFI_MPLS_VPN";
971 else
972 return "Unknown SAFI";
973}
974
975/* Send route refresh message to the peer. */
976void
977bgp_route_refresh_send (struct peer *peer, afi_t afi, safi_t safi,
978 u_char orf_type, u_char when_to_refresh, int remove)
979{
980 struct stream *s;
981 struct stream *packet;
982 int length;
983 struct bgp_filter *filter;
984 int orf_refresh = 0;
985
986#ifdef DISABLE_BGP_ANNOUNCE
987 return;
988#endif /* DISABLE_BGP_ANNOUNCE */
989
990 filter = &peer->filter[afi][safi];
991
992 /* Adjust safi code. */
993 if (safi == SAFI_MPLS_VPN)
994 safi = BGP_SAFI_VPNV4;
995
996 s = stream_new (BGP_MAX_PACKET_SIZE);
997
998 /* Make BGP update packet. */
999 if (CHECK_FLAG (peer->cap, PEER_CAP_REFRESH_NEW_RCV))
1000 bgp_packet_set_marker (s, BGP_MSG_ROUTE_REFRESH_NEW);
1001 else
1002 bgp_packet_set_marker (s, BGP_MSG_ROUTE_REFRESH_OLD);
1003
1004 /* Encode Route Refresh message. */
1005 stream_putw (s, afi);
1006 stream_putc (s, 0);
1007 stream_putc (s, safi);
1008
1009 if (orf_type == ORF_TYPE_PREFIX
1010 || orf_type == ORF_TYPE_PREFIX_OLD)
1011 if (remove || filter->plist[FILTER_IN].plist)
1012 {
1013 u_int16_t orf_len;
1014 unsigned long orfp;
1015
1016 orf_refresh = 1;
1017 stream_putc (s, when_to_refresh);
1018 stream_putc (s, orf_type);
1019 orfp = stream_get_putp (s);
1020 stream_putw (s, 0);
1021
1022 if (remove)
1023 {
1024 UNSET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_ORF_PREFIX_SEND);
1025 stream_putc (s, ORF_COMMON_PART_REMOVE_ALL);
1026 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001027 zlog_debug ("%s sending REFRESH_REQ to remove ORF(%d) (%s) for afi/safi: %d/%d",
paul718e3742002-12-13 20:15:29 +00001028 peer->host, orf_type,
1029 (when_to_refresh == REFRESH_DEFER ? "defer" : "immediate"),
1030 afi, safi);
1031 }
1032 else
1033 {
1034 SET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_ORF_PREFIX_SEND);
1035 prefix_bgp_orf_entry (s, filter->plist[FILTER_IN].plist,
1036 ORF_COMMON_PART_ADD, ORF_COMMON_PART_PERMIT,
1037 ORF_COMMON_PART_DENY);
1038 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001039 zlog_debug ("%s sending REFRESH_REQ with pfxlist ORF(%d) (%s) for afi/safi: %d/%d",
paul718e3742002-12-13 20:15:29 +00001040 peer->host, orf_type,
1041 (when_to_refresh == REFRESH_DEFER ? "defer" : "immediate"),
1042 afi, safi);
1043 }
1044
1045 /* Total ORF Entry Len. */
1046 orf_len = stream_get_putp (s) - orfp - 2;
1047 stream_putw_at (s, orfp, orf_len);
1048 }
1049
1050 /* Set packet size. */
1051 length = bgp_packet_set_size (s);
1052
1053 if (BGP_DEBUG (normal, NORMAL))
1054 {
1055 if (! orf_refresh)
ajs6b514742004-12-08 21:03:23 +00001056 zlog_debug ("%s sending REFRESH_REQ for afi/safi: %d/%d",
paul718e3742002-12-13 20:15:29 +00001057 peer->host, afi, safi);
ajs6b514742004-12-08 21:03:23 +00001058 zlog_debug ("%s send message type %d, length (incl. header) %d",
paul718e3742002-12-13 20:15:29 +00001059 peer->host, CHECK_FLAG (peer->cap, PEER_CAP_REFRESH_NEW_RCV) ?
1060 BGP_MSG_ROUTE_REFRESH_NEW : BGP_MSG_ROUTE_REFRESH_OLD, length);
1061 }
1062
1063 /* Make real packet. */
1064 packet = bgp_packet_dup (s);
1065 stream_free (s);
1066
1067 /* Add packet to the peer. */
1068 bgp_packet_add (peer, packet);
1069
pauleb821182004-05-01 08:44:08 +00001070 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +00001071}
1072
1073/* Send capability message to the peer. */
1074void
1075bgp_capability_send (struct peer *peer, afi_t afi, safi_t safi,
1076 int capability_code, int action)
1077{
1078 struct stream *s;
1079 struct stream *packet;
1080 int length;
1081
1082 /* Adjust safi code. */
1083 if (safi == SAFI_MPLS_VPN)
1084 safi = BGP_SAFI_VPNV4;
1085
1086 s = stream_new (BGP_MAX_PACKET_SIZE);
1087
1088 /* Make BGP update packet. */
1089 bgp_packet_set_marker (s, BGP_MSG_CAPABILITY);
1090
1091 /* Encode MP_EXT capability. */
1092 if (capability_code == CAPABILITY_CODE_MP)
1093 {
1094 stream_putc (s, action);
1095 stream_putc (s, CAPABILITY_CODE_MP);
1096 stream_putc (s, CAPABILITY_CODE_MP_LEN);
1097 stream_putw (s, afi);
1098 stream_putc (s, 0);
1099 stream_putc (s, safi);
1100
1101 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001102 zlog_debug ("%s sending CAPABILITY has %s MP_EXT CAP for afi/safi: %d/%d",
paul718e3742002-12-13 20:15:29 +00001103 peer->host, action == CAPABILITY_ACTION_SET ?
1104 "Advertising" : "Removing", afi, safi);
1105 }
1106
paul718e3742002-12-13 20:15:29 +00001107 /* Set packet size. */
1108 length = bgp_packet_set_size (s);
1109
1110 /* Make real packet. */
1111 packet = bgp_packet_dup (s);
1112 stream_free (s);
1113
1114 /* Add packet to the peer. */
1115 bgp_packet_add (peer, packet);
1116
1117 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001118 zlog_debug ("%s send message type %d, length (incl. header) %d",
paul718e3742002-12-13 20:15:29 +00001119 peer->host, BGP_MSG_CAPABILITY, length);
1120
pauleb821182004-05-01 08:44:08 +00001121 BGP_WRITE_ON (peer->t_write, bgp_write, peer->fd);
paul718e3742002-12-13 20:15:29 +00001122}
1123
1124/* RFC1771 6.8 Connection collision detection. */
1125int
pauleb821182004-05-01 08:44:08 +00001126bgp_collision_detect (struct peer *new, struct in_addr remote_id)
paul718e3742002-12-13 20:15:29 +00001127{
pauleb821182004-05-01 08:44:08 +00001128 struct peer *peer;
paul718e3742002-12-13 20:15:29 +00001129 struct listnode *nn;
1130 struct bgp *bgp;
1131
1132 bgp = bgp_get_default ();
1133 if (! bgp)
1134 return 0;
1135
1136 /* Upon receipt of an OPEN message, the local system must examine
1137 all of its connections that are in the OpenConfirm state. A BGP
1138 speaker may also examine connections in an OpenSent state if it
1139 knows the BGP Identifier of the peer by means outside of the
1140 protocol. If among these connections there is a connection to a
1141 remote BGP speaker whose BGP Identifier equals the one in the
1142 OPEN message, then the local system performs the following
1143 collision resolution procedure: */
1144
1145 LIST_LOOP (bgp->peer, peer, nn)
1146 {
1147 /* Under OpenConfirm status, local peer structure already hold
1148 remote router ID. */
pauleb821182004-05-01 08:44:08 +00001149
1150 if (peer != new
1151 && (peer->status == OpenConfirm || peer->status == OpenSent)
1152 && sockunion_same (&peer->su, &new->su))
1153 {
paul718e3742002-12-13 20:15:29 +00001154 /* 1. The BGP Identifier of the local system is compared to
1155 the BGP Identifier of the remote system (as specified in
1156 the OPEN message). */
1157
1158 if (ntohl (peer->local_id.s_addr) < ntohl (remote_id.s_addr))
1159 {
1160 /* 2. If the value of the local BGP Identifier is less
1161 than the remote one, the local system closes BGP
1162 connection that already exists (the one that is
1163 already in the OpenConfirm state), and accepts BGP
1164 connection initiated by the remote system. */
1165
pauleb821182004-05-01 08:44:08 +00001166 if (peer->fd >= 0)
hassoe0701b72004-05-20 09:19:34 +00001167 bgp_notify_send (peer, BGP_NOTIFY_CEASE, BGP_NOTIFY_CEASE_COLLISION_RESOLUTION);
paul718e3742002-12-13 20:15:29 +00001168 return 1;
1169 }
1170 else
1171 {
1172 /* 3. Otherwise, the local system closes newly created
1173 BGP connection (the one associated with the newly
1174 received OPEN message), and continues to use the
1175 existing one (the one that is already in the
1176 OpenConfirm state). */
1177
pauleb821182004-05-01 08:44:08 +00001178 if (new->fd >= 0)
paulf5ba3872004-07-09 12:11:31 +00001179 bgp_notify_send (new, BGP_NOTIFY_CEASE,
1180 BGP_NOTIFY_CEASE_COLLISION_RESOLUTION);
paul718e3742002-12-13 20:15:29 +00001181 return -1;
1182 }
pauleb821182004-05-01 08:44:08 +00001183 }
1184 }
paul718e3742002-12-13 20:15:29 +00001185 return 0;
1186}
1187
1188int
1189bgp_open_receive (struct peer *peer, bgp_size_t size)
1190{
1191 int ret;
1192 u_char version;
1193 u_char optlen;
1194 u_int16_t holdtime;
1195 u_int16_t send_holdtime;
1196 as_t remote_as;
1197 struct peer *realpeer;
1198 struct in_addr remote_id;
1199 int capability;
paul5228ad22004-06-04 17:58:18 +00001200 u_int8_t notify_data_remote_as[2];
1201 u_int8_t notify_data_remote_id[4];
paul718e3742002-12-13 20:15:29 +00001202
1203 realpeer = NULL;
1204
1205 /* Parse open packet. */
1206 version = stream_getc (peer->ibuf);
1207 memcpy (notify_data_remote_as, stream_pnt (peer->ibuf), 2);
1208 remote_as = stream_getw (peer->ibuf);
1209 holdtime = stream_getw (peer->ibuf);
1210 memcpy (notify_data_remote_id, stream_pnt (peer->ibuf), 4);
1211 remote_id.s_addr = stream_get_ipv4 (peer->ibuf);
1212
1213 /* Receive OPEN message log */
1214 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001215 zlog_debug ("%s rcv OPEN, version %d, remote-as %d, holdtime %d, id %s",
paul718e3742002-12-13 20:15:29 +00001216 peer->host, version, remote_as, holdtime,
1217 inet_ntoa (remote_id));
1218
1219 /* Lookup peer from Open packet. */
1220 if (CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
1221 {
1222 int as = 0;
1223
1224 realpeer = peer_lookup_with_open (&peer->su, remote_as, &remote_id, &as);
1225
1226 if (! realpeer)
1227 {
1228 /* Peer's source IP address is check in bgp_accept(), so this
1229 must be AS number mismatch or remote-id configuration
1230 mismatch. */
1231 if (as)
1232 {
1233 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001234 zlog_debug ("%s bad OPEN, wrong router identifier %s",
1235 peer->host, inet_ntoa (remote_id));
1236 bgp_notify_send_with_data (peer, BGP_NOTIFY_OPEN_ERR,
1237 BGP_NOTIFY_OPEN_BAD_BGP_IDENT,
1238 notify_data_remote_id, 4);
paul718e3742002-12-13 20:15:29 +00001239 }
1240 else
1241 {
1242 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001243 zlog_debug ("%s bad OPEN, remote AS is %d, expected %d",
1244 peer->host, remote_as, peer->as);
1245 bgp_notify_send_with_data (peer, BGP_NOTIFY_OPEN_ERR,
1246 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1247 notify_data_remote_as, 2);
paul718e3742002-12-13 20:15:29 +00001248 }
1249 return -1;
1250 }
1251 }
1252
1253 /* When collision is detected and this peer is closed. Retrun
1254 immidiately. */
1255 ret = bgp_collision_detect (peer, remote_id);
1256 if (ret < 0)
1257 return ret;
1258
pauleb821182004-05-01 08:44:08 +00001259 /* Hack part. */
1260 if (CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
1261 {
hasso93406d82005-02-02 14:40:33 +00001262 if (realpeer->status == Established
1263 && CHECK_FLAG (realpeer->sflags, PEER_STATUS_NSF_MODE))
1264 {
1265 realpeer->last_reset = PEER_DOWN_NSF_CLOSE_SESSION;
1266 SET_FLAG (realpeer->sflags, PEER_STATUS_NSF_WAIT);
1267 }
1268 else if (ret == 0 && realpeer->status != Active
1269 && realpeer->status != OpenSent
1270 && realpeer->status != OpenConfirm)
1271
pauleb821182004-05-01 08:44:08 +00001272 {
1273 if (BGP_DEBUG (events, EVENTS))
hasso93406d82005-02-02 14:40:33 +00001274 zlog_debug ("%s peer status is %s close connection",
1275 realpeer->host, LOOKUP (bgp_status_msg,
1276 realpeer->status));
1277 bgp_notify_send (peer, BGP_NOTIFY_CEASE,
1278 BGP_NOTIFY_CEASE_CONNECT_REJECT);
1279
pauleb821182004-05-01 08:44:08 +00001280 return -1;
1281 }
1282
1283 if (BGP_DEBUG (events, EVENTS))
ajs6b514742004-12-08 21:03:23 +00001284 zlog_debug ("%s [Event] Transfer temporary BGP peer to existing one",
pauleb821182004-05-01 08:44:08 +00001285 peer->host);
1286
1287 bgp_stop (realpeer);
1288
1289 /* Transfer file descriptor. */
1290 realpeer->fd = peer->fd;
1291 peer->fd = -1;
1292
1293 /* Transfer input buffer. */
1294 stream_free (realpeer->ibuf);
1295 realpeer->ibuf = peer->ibuf;
1296 realpeer->packet_size = peer->packet_size;
1297 peer->ibuf = NULL;
1298
1299 /* Transfer status. */
1300 realpeer->status = peer->status;
1301 bgp_stop (peer);
1302
1303 /* peer pointer change. Open packet send to neighbor. */
1304 peer = realpeer;
1305 bgp_open_send (peer);
1306 if (peer->fd < 0)
1307 {
1308 zlog_err ("bgp_open_receive peer's fd is negative value %d",
1309 peer->fd);
1310 return -1;
1311 }
1312 BGP_READ_ON (peer->t_read, bgp_read, peer->fd);
1313 }
1314
paul718e3742002-12-13 20:15:29 +00001315 /* remote router-id check. */
1316 if (remote_id.s_addr == 0
1317 || ntohl (remote_id.s_addr) >= 0xe0000000
1318 || ntohl (peer->local_id.s_addr) == ntohl (remote_id.s_addr))
1319 {
1320 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001321 zlog_debug ("%s bad OPEN, wrong router identifier %s",
paul718e3742002-12-13 20:15:29 +00001322 peer->host, inet_ntoa (remote_id));
1323 bgp_notify_send_with_data (peer,
1324 BGP_NOTIFY_OPEN_ERR,
1325 BGP_NOTIFY_OPEN_BAD_BGP_IDENT,
1326 notify_data_remote_id, 4);
1327 return -1;
1328 }
1329
1330 /* Set remote router-id */
1331 peer->remote_id = remote_id;
1332
1333 /* Peer BGP version check. */
1334 if (version != BGP_VERSION_4)
1335 {
paul5228ad22004-06-04 17:58:18 +00001336 u_int8_t maxver = BGP_VERSION_4;
paul718e3742002-12-13 20:15:29 +00001337 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001338 zlog_debug ("%s bad protocol version, remote requested %d, local request %d",
paul718e3742002-12-13 20:15:29 +00001339 peer->host, version, BGP_VERSION_4);
1340 bgp_notify_send_with_data (peer,
1341 BGP_NOTIFY_OPEN_ERR,
1342 BGP_NOTIFY_OPEN_UNSUP_VERSION,
paul5228ad22004-06-04 17:58:18 +00001343 &maxver, 1);
paul718e3742002-12-13 20:15:29 +00001344 return -1;
1345 }
1346
1347 /* Check neighbor as number. */
1348 if (remote_as != peer->as)
1349 {
1350 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001351 zlog_debug ("%s bad OPEN, remote AS is %d, expected %d",
paul718e3742002-12-13 20:15:29 +00001352 peer->host, remote_as, peer->as);
1353 bgp_notify_send_with_data (peer,
1354 BGP_NOTIFY_OPEN_ERR,
1355 BGP_NOTIFY_OPEN_BAD_PEER_AS,
1356 notify_data_remote_as, 2);
1357 return -1;
1358 }
1359
1360 /* From the rfc: Upon receipt of an OPEN message, a BGP speaker MUST
1361 calculate the value of the Hold Timer by using the smaller of its
1362 configured Hold Time and the Hold Time received in the OPEN message.
1363 The Hold Time MUST be either zero or at least three seconds. An
1364 implementation may reject connections on the basis of the Hold Time. */
1365
1366 if (holdtime < 3 && holdtime != 0)
1367 {
1368 bgp_notify_send (peer,
1369 BGP_NOTIFY_OPEN_ERR,
1370 BGP_NOTIFY_OPEN_UNACEP_HOLDTIME);
1371 return -1;
1372 }
1373
1374 /* From the rfc: A reasonable maximum time between KEEPALIVE messages
1375 would be one third of the Hold Time interval. KEEPALIVE messages
1376 MUST NOT be sent more frequently than one per second. An
1377 implementation MAY adjust the rate at which it sends KEEPALIVE
1378 messages as a function of the Hold Time interval. */
1379
1380 if (CHECK_FLAG (peer->config, PEER_CONFIG_TIMER))
1381 send_holdtime = peer->holdtime;
1382 else
1383 send_holdtime = peer->bgp->default_holdtime;
1384
1385 if (holdtime < send_holdtime)
1386 peer->v_holdtime = holdtime;
1387 else
1388 peer->v_holdtime = send_holdtime;
1389
1390 peer->v_keepalive = peer->v_holdtime / 3;
1391
1392 /* Open option part parse. */
1393 capability = 0;
1394 optlen = stream_getc (peer->ibuf);
1395 if (optlen != 0)
1396 {
1397 ret = bgp_open_option_parse (peer, optlen, &capability);
1398 if (ret < 0)
1399 return ret;
1400
1401 stream_forward (peer->ibuf, optlen);
1402 }
1403 else
1404 {
1405 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001406 zlog_debug ("%s rcvd OPEN w/ OPTION parameter len: 0",
paul718e3742002-12-13 20:15:29 +00001407 peer->host);
1408 }
1409
1410 /* Override capability. */
1411 if (! capability || CHECK_FLAG (peer->flags, PEER_FLAG_OVERRIDE_CAPABILITY))
1412 {
1413 peer->afc_nego[AFI_IP][SAFI_UNICAST] = peer->afc[AFI_IP][SAFI_UNICAST];
1414 peer->afc_nego[AFI_IP][SAFI_MULTICAST] = peer->afc[AFI_IP][SAFI_MULTICAST];
1415 peer->afc_nego[AFI_IP6][SAFI_UNICAST] = peer->afc[AFI_IP6][SAFI_UNICAST];
1416 peer->afc_nego[AFI_IP6][SAFI_MULTICAST] = peer->afc[AFI_IP6][SAFI_MULTICAST];
1417 }
1418
1419 /* Get sockname. */
1420 bgp_getsockname (peer);
1421
1422 BGP_EVENT_ADD (peer, Receive_OPEN_message);
1423
1424 peer->packet_size = 0;
1425 if (peer->ibuf)
1426 stream_reset (peer->ibuf);
1427
1428 return 0;
1429}
1430
1431/* Parse BGP Update packet and make attribute object. */
1432int
1433bgp_update_receive (struct peer *peer, bgp_size_t size)
1434{
1435 int ret;
1436 u_char *end;
1437 struct stream *s;
1438 struct attr attr;
1439 bgp_size_t attribute_len;
1440 bgp_size_t update_len;
1441 bgp_size_t withdraw_len;
1442 struct bgp_nlri update;
1443 struct bgp_nlri withdraw;
1444 struct bgp_nlri mp_update;
1445 struct bgp_nlri mp_withdraw;
paule01f9cb2004-07-09 17:48:53 +00001446 char attrstr[BUFSIZ] = "";
paul718e3742002-12-13 20:15:29 +00001447
1448 /* Status must be Established. */
1449 if (peer->status != Established)
1450 {
1451 zlog_err ("%s [FSM] Update packet received under status %s",
1452 peer->host, LOOKUP (bgp_status_msg, peer->status));
1453 bgp_notify_send (peer, BGP_NOTIFY_FSM_ERR, 0);
1454 return -1;
1455 }
1456
1457 /* Set initial values. */
1458 memset (&attr, 0, sizeof (struct attr));
1459 memset (&update, 0, sizeof (struct bgp_nlri));
1460 memset (&withdraw, 0, sizeof (struct bgp_nlri));
1461 memset (&mp_update, 0, sizeof (struct bgp_nlri));
1462 memset (&mp_withdraw, 0, sizeof (struct bgp_nlri));
1463
1464 s = peer->ibuf;
1465 end = stream_pnt (s) + size;
1466
1467 /* RFC1771 6.3 If the Unfeasible Routes Length or Total Attribute
1468 Length is too large (i.e., if Unfeasible Routes Length + Total
1469 Attribute Length + 23 exceeds the message Length), then the Error
1470 Subcode is set to Malformed Attribute List. */
1471 if (stream_pnt (s) + 2 > end)
1472 {
1473 zlog_err ("%s [Error] Update packet error"
1474 " (packet length is short for unfeasible length)",
1475 peer->host);
1476 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
1477 BGP_NOTIFY_UPDATE_MAL_ATTR);
1478 return -1;
1479 }
1480
1481 /* Unfeasible Route Length. */
1482 withdraw_len = stream_getw (s);
1483
1484 /* Unfeasible Route Length check. */
1485 if (stream_pnt (s) + withdraw_len > end)
1486 {
1487 zlog_err ("%s [Error] Update packet error"
1488 " (packet unfeasible length overflow %d)",
1489 peer->host, withdraw_len);
1490 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
1491 BGP_NOTIFY_UPDATE_MAL_ATTR);
1492 return -1;
1493 }
1494
1495 /* Unfeasible Route packet format check. */
1496 if (withdraw_len > 0)
1497 {
1498 ret = bgp_nlri_sanity_check (peer, AFI_IP, stream_pnt (s), withdraw_len);
1499 if (ret < 0)
1500 return -1;
1501
1502 if (BGP_DEBUG (packet, PACKET_RECV))
ajs6b514742004-12-08 21:03:23 +00001503 zlog_debug ("%s [Update:RECV] Unfeasible NLRI received", peer->host);
paul718e3742002-12-13 20:15:29 +00001504
1505 withdraw.afi = AFI_IP;
1506 withdraw.safi = SAFI_UNICAST;
1507 withdraw.nlri = stream_pnt (s);
1508 withdraw.length = withdraw_len;
1509 stream_forward (s, withdraw_len);
1510 }
1511
1512 /* Attribute total length check. */
1513 if (stream_pnt (s) + 2 > end)
1514 {
1515 zlog_warn ("%s [Error] Packet Error"
1516 " (update packet is short for attribute length)",
1517 peer->host);
1518 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
1519 BGP_NOTIFY_UPDATE_MAL_ATTR);
1520 return -1;
1521 }
1522
1523 /* Fetch attribute total length. */
1524 attribute_len = stream_getw (s);
1525
1526 /* Attribute length check. */
1527 if (stream_pnt (s) + attribute_len > end)
1528 {
1529 zlog_warn ("%s [Error] Packet Error"
1530 " (update packet attribute length overflow %d)",
1531 peer->host, attribute_len);
1532 bgp_notify_send (peer, BGP_NOTIFY_UPDATE_ERR,
1533 BGP_NOTIFY_UPDATE_MAL_ATTR);
1534 return -1;
1535 }
1536
1537 /* Parse attribute when it exists. */
1538 if (attribute_len)
1539 {
1540 ret = bgp_attr_parse (peer, &attr, attribute_len,
1541 &mp_update, &mp_withdraw);
1542 if (ret < 0)
1543 return -1;
1544 }
1545
1546 /* Logging the attribute. */
1547 if (BGP_DEBUG (update, UPDATE_IN))
1548 {
paule01f9cb2004-07-09 17:48:53 +00001549 ret= bgp_dump_attr (peer, &attr, attrstr, BUFSIZ);
1550
1551 if (ret)
ajs6b514742004-12-08 21:03:23 +00001552 zlog (peer->log, LOG_DEBUG, "%s rcvd UPDATE w/ attr: %s",
paule01f9cb2004-07-09 17:48:53 +00001553 peer->host, attrstr);
paul718e3742002-12-13 20:15:29 +00001554 }
1555
1556 /* Network Layer Reachability Information. */
1557 update_len = end - stream_pnt (s);
1558
1559 if (update_len)
1560 {
1561 /* Check NLRI packet format and prefix length. */
1562 ret = bgp_nlri_sanity_check (peer, AFI_IP, stream_pnt (s), update_len);
1563 if (ret < 0)
1564 return -1;
1565
1566 /* Set NLRI portion to structure. */
1567 update.afi = AFI_IP;
1568 update.safi = SAFI_UNICAST;
1569 update.nlri = stream_pnt (s);
1570 update.length = update_len;
1571 stream_forward (s, update_len);
1572 }
1573
1574 /* NLRI is processed only when the peer is configured specific
1575 Address Family and Subsequent Address Family. */
1576 if (peer->afc[AFI_IP][SAFI_UNICAST])
1577 {
1578 if (withdraw.length)
1579 bgp_nlri_parse (peer, NULL, &withdraw);
1580
1581 if (update.length)
1582 {
1583 /* We check well-known attribute only for IPv4 unicast
1584 update. */
1585 ret = bgp_attr_check (peer, &attr);
1586 if (ret < 0)
1587 return -1;
1588
1589 bgp_nlri_parse (peer, &attr, &update);
1590 }
paule01f9cb2004-07-09 17:48:53 +00001591
hassof4184462005-02-01 20:13:16 +00001592 if (mp_update.length
1593 && mp_update.afi == AFI_IP
1594 && mp_update.safi == SAFI_UNICAST)
1595 bgp_nlri_parse (peer, &attr, &mp_update);
1596
1597 if (mp_withdraw.length
1598 && mp_withdraw.afi == AFI_IP
1599 && mp_withdraw.safi == SAFI_UNICAST)
1600 bgp_nlri_parse (peer, NULL, &mp_withdraw);
1601
paule01f9cb2004-07-09 17:48:53 +00001602 if (! attribute_len && ! withdraw_len)
1603 {
1604 /* End-of-RIB received */
hasso93406d82005-02-02 14:40:33 +00001605 SET_FLAG (peer->af_sflags[AFI_IP][SAFI_UNICAST],
1606 PEER_STATUS_EOR_RECEIVED);
paule01f9cb2004-07-09 17:48:53 +00001607
hasso93406d82005-02-02 14:40:33 +00001608 /* NSF delete stale route */
1609 if (peer->nsf[AFI_IP][SAFI_UNICAST])
1610 bgp_clear_stale_route (peer, AFI_IP, SAFI_UNICAST);
1611
1612 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001613 zlog (peer->log, LOG_DEBUG, "rcvd End-of-RIB for IPv4 Unicast from %s",
paule01f9cb2004-07-09 17:48:53 +00001614 peer->host);
1615 }
paul718e3742002-12-13 20:15:29 +00001616 }
1617 if (peer->afc[AFI_IP][SAFI_MULTICAST])
1618 {
1619 if (mp_update.length
1620 && mp_update.afi == AFI_IP
1621 && mp_update.safi == SAFI_MULTICAST)
1622 bgp_nlri_parse (peer, &attr, &mp_update);
1623
1624 if (mp_withdraw.length
1625 && mp_withdraw.afi == AFI_IP
1626 && mp_withdraw.safi == SAFI_MULTICAST)
1627 bgp_nlri_parse (peer, NULL, &mp_withdraw);
paule01f9cb2004-07-09 17:48:53 +00001628
hasso93406d82005-02-02 14:40:33 +00001629 if (! withdraw_len
paule01f9cb2004-07-09 17:48:53 +00001630 && mp_withdraw.afi == AFI_IP
1631 && mp_withdraw.safi == SAFI_MULTICAST
1632 && mp_withdraw.length == 0)
1633 {
1634 /* End-of-RIB received */
hasso93406d82005-02-02 14:40:33 +00001635 SET_FLAG (peer->af_sflags[AFI_IP][SAFI_MULTICAST],
1636 PEER_STATUS_EOR_RECEIVED);
paule01f9cb2004-07-09 17:48:53 +00001637
hasso93406d82005-02-02 14:40:33 +00001638 /* NSF delete stale route */
1639 if (peer->nsf[AFI_IP][SAFI_MULTICAST])
1640 bgp_clear_stale_route (peer, AFI_IP, SAFI_MULTICAST);
1641
1642 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001643 zlog (peer->log, LOG_DEBUG, "rcvd End-of-RIB for IPv4 Multicast from %s",
paule01f9cb2004-07-09 17:48:53 +00001644 peer->host);
1645 }
paul718e3742002-12-13 20:15:29 +00001646 }
1647 if (peer->afc[AFI_IP6][SAFI_UNICAST])
1648 {
1649 if (mp_update.length
1650 && mp_update.afi == AFI_IP6
1651 && mp_update.safi == SAFI_UNICAST)
1652 bgp_nlri_parse (peer, &attr, &mp_update);
1653
1654 if (mp_withdraw.length
1655 && mp_withdraw.afi == AFI_IP6
1656 && mp_withdraw.safi == SAFI_UNICAST)
1657 bgp_nlri_parse (peer, NULL, &mp_withdraw);
paule01f9cb2004-07-09 17:48:53 +00001658
hasso93406d82005-02-02 14:40:33 +00001659 if (! withdraw_len
paule01f9cb2004-07-09 17:48:53 +00001660 && mp_withdraw.afi == AFI_IP6
1661 && mp_withdraw.safi == SAFI_UNICAST
1662 && mp_withdraw.length == 0)
1663 {
1664 /* End-of-RIB received */
hasso93406d82005-02-02 14:40:33 +00001665 SET_FLAG (peer->af_sflags[AFI_IP6][SAFI_UNICAST], PEER_STATUS_EOR_RECEIVED);
paule01f9cb2004-07-09 17:48:53 +00001666
hasso93406d82005-02-02 14:40:33 +00001667 /* NSF delete stale route */
1668 if (peer->nsf[AFI_IP6][SAFI_UNICAST])
1669 bgp_clear_stale_route (peer, AFI_IP6, SAFI_UNICAST);
1670
1671 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001672 zlog (peer->log, LOG_DEBUG, "rcvd End-of-RIB for IPv6 Unicast from %s",
paule01f9cb2004-07-09 17:48:53 +00001673 peer->host);
1674 }
paul718e3742002-12-13 20:15:29 +00001675 }
1676 if (peer->afc[AFI_IP6][SAFI_MULTICAST])
1677 {
1678 if (mp_update.length
1679 && mp_update.afi == AFI_IP6
1680 && mp_update.safi == SAFI_MULTICAST)
1681 bgp_nlri_parse (peer, &attr, &mp_update);
1682
1683 if (mp_withdraw.length
1684 && mp_withdraw.afi == AFI_IP6
1685 && mp_withdraw.safi == SAFI_MULTICAST)
1686 bgp_nlri_parse (peer, NULL, &mp_withdraw);
paule01f9cb2004-07-09 17:48:53 +00001687
hasso93406d82005-02-02 14:40:33 +00001688 if (! withdraw_len
paule01f9cb2004-07-09 17:48:53 +00001689 && mp_withdraw.afi == AFI_IP6
1690 && mp_withdraw.safi == SAFI_MULTICAST
1691 && mp_withdraw.length == 0)
1692 {
1693 /* End-of-RIB received */
1694
hasso93406d82005-02-02 14:40:33 +00001695 /* NSF delete stale route */
1696 if (peer->nsf[AFI_IP6][SAFI_MULTICAST])
1697 bgp_clear_stale_route (peer, AFI_IP6, SAFI_MULTICAST);
1698
paule01f9cb2004-07-09 17:48:53 +00001699 if (BGP_DEBUG (update, UPDATE_IN))
ajs6b514742004-12-08 21:03:23 +00001700 zlog (peer->log, LOG_DEBUG, "rcvd End-of-RIB for IPv6 Multicast from %s",
paule01f9cb2004-07-09 17:48:53 +00001701 peer->host);
1702 }
paul718e3742002-12-13 20:15:29 +00001703 }
1704 if (peer->afc[AFI_IP][SAFI_MPLS_VPN])
1705 {
1706 if (mp_update.length
1707 && mp_update.afi == AFI_IP
1708 && mp_update.safi == BGP_SAFI_VPNV4)
1709 bgp_nlri_parse_vpnv4 (peer, &attr, &mp_update);
1710
1711 if (mp_withdraw.length
1712 && mp_withdraw.afi == AFI_IP
1713 && mp_withdraw.safi == BGP_SAFI_VPNV4)
1714 bgp_nlri_parse_vpnv4 (peer, NULL, &mp_withdraw);
paule01f9cb2004-07-09 17:48:53 +00001715
hasso93406d82005-02-02 14:40:33 +00001716 if (! withdraw_len
paule01f9cb2004-07-09 17:48:53 +00001717 && mp_withdraw.afi == AFI_IP
1718 && mp_withdraw.safi == BGP_SAFI_VPNV4
1719 && mp_withdraw.length == 0)
1720 {
1721 /* End-of-RIB received */
1722
1723 if (BGP_DEBUG (update, UPDATE_IN))
ajs6b514742004-12-08 21:03:23 +00001724 zlog (peer->log, LOG_DEBUG, "rcvd End-of-RIB for VPNv4 Unicast from %s",
paule01f9cb2004-07-09 17:48:53 +00001725 peer->host);
1726 }
paul718e3742002-12-13 20:15:29 +00001727 }
1728
1729 /* Everything is done. We unintern temporary structures which
1730 interned in bgp_attr_parse(). */
1731 if (attr.aspath)
1732 aspath_unintern (attr.aspath);
1733 if (attr.community)
1734 community_unintern (attr.community);
1735 if (attr.ecommunity)
1736 ecommunity_unintern (attr.ecommunity);
1737 if (attr.cluster)
1738 cluster_unintern (attr.cluster);
1739 if (attr.transit)
1740 transit_unintern (attr.transit);
1741
1742 /* If peering is stopped due to some reason, do not generate BGP
1743 event. */
1744 if (peer->status != Established)
1745 return 0;
1746
1747 /* Increment packet counter. */
1748 peer->update_in++;
1749 peer->update_time = time (NULL);
1750
1751 /* Generate BGP event. */
1752 BGP_EVENT_ADD (peer, Receive_UPDATE_message);
1753
1754 return 0;
1755}
1756
1757/* Notify message treatment function. */
1758void
1759bgp_notify_receive (struct peer *peer, bgp_size_t size)
1760{
1761 struct bgp_notify bgp_notify;
1762
1763 if (peer->notify.data)
1764 {
1765 XFREE (MTYPE_TMP, peer->notify.data);
1766 peer->notify.data = NULL;
1767 peer->notify.length = 0;
1768 }
1769
1770 bgp_notify.code = stream_getc (peer->ibuf);
1771 bgp_notify.subcode = stream_getc (peer->ibuf);
1772 bgp_notify.length = size - 2;
1773 bgp_notify.data = NULL;
1774
1775 /* Preserv notify code and sub code. */
1776 peer->notify.code = bgp_notify.code;
1777 peer->notify.subcode = bgp_notify.subcode;
1778 /* For further diagnostic record returned Data. */
1779 if (bgp_notify.length)
1780 {
1781 peer->notify.length = size - 2;
1782 peer->notify.data = XMALLOC (MTYPE_TMP, size - 2);
1783 memcpy (peer->notify.data, stream_pnt (peer->ibuf), size - 2);
1784 }
1785
1786 /* For debug */
1787 {
1788 int i;
1789 int first = 0;
1790 char c[4];
1791
1792 if (bgp_notify.length)
1793 {
1794 bgp_notify.data = XMALLOC (MTYPE_TMP, bgp_notify.length * 3);
1795 for (i = 0; i < bgp_notify.length; i++)
1796 if (first)
1797 {
1798 sprintf (c, " %02x", stream_getc (peer->ibuf));
1799 strcat (bgp_notify.data, c);
1800 }
1801 else
1802 {
1803 first = 1;
1804 sprintf (c, "%02x", stream_getc (peer->ibuf));
1805 strcpy (bgp_notify.data, c);
1806 }
1807 }
1808
1809 bgp_notify_print(peer, &bgp_notify, "received");
1810 if (bgp_notify.data)
1811 XFREE (MTYPE_TMP, bgp_notify.data);
1812 }
1813
1814 /* peer count update */
1815 peer->notify_in++;
1816
hassoe0701b72004-05-20 09:19:34 +00001817 if (peer->status == Established)
1818 peer->last_reset = PEER_DOWN_NOTIFY_RECEIVED;
1819
paul718e3742002-12-13 20:15:29 +00001820 /* We have to check for Notify with Unsupported Optional Parameter.
1821 in that case we fallback to open without the capability option.
1822 But this done in bgp_stop. We just mark it here to avoid changing
1823 the fsm tables. */
1824 if (bgp_notify.code == BGP_NOTIFY_OPEN_ERR &&
1825 bgp_notify.subcode == BGP_NOTIFY_OPEN_UNSUP_PARAM )
1826 UNSET_FLAG (peer->sflags, PEER_STATUS_CAPABILITY_OPEN);
1827
1828 /* Also apply to Unsupported Capability until remote router support
1829 capability. */
1830 if (bgp_notify.code == BGP_NOTIFY_OPEN_ERR &&
1831 bgp_notify.subcode == BGP_NOTIFY_OPEN_UNSUP_CAPBL)
1832 UNSET_FLAG (peer->sflags, PEER_STATUS_CAPABILITY_OPEN);
1833
1834 BGP_EVENT_ADD (peer, Receive_NOTIFICATION_message);
1835}
1836
1837/* Keepalive treatment function -- get keepalive send keepalive */
1838void
1839bgp_keepalive_receive (struct peer *peer, bgp_size_t size)
1840{
1841 if (BGP_DEBUG (keepalive, KEEPALIVE))
ajs6b514742004-12-08 21:03:23 +00001842 zlog_debug ("%s KEEPALIVE rcvd", peer->host);
paul718e3742002-12-13 20:15:29 +00001843
1844 BGP_EVENT_ADD (peer, Receive_KEEPALIVE_message);
1845}
1846
1847/* Route refresh message is received. */
1848void
1849bgp_route_refresh_receive (struct peer *peer, bgp_size_t size)
1850{
1851 afi_t afi;
1852 safi_t safi;
1853 u_char reserved;
1854 struct stream *s;
1855
1856 /* If peer does not have the capability, send notification. */
1857 if (! CHECK_FLAG (peer->cap, PEER_CAP_REFRESH_ADV))
1858 {
1859 plog_err (peer->log, "%s [Error] BGP route refresh is not enabled",
1860 peer->host);
1861 bgp_notify_send (peer,
1862 BGP_NOTIFY_HEADER_ERR,
1863 BGP_NOTIFY_HEADER_BAD_MESTYPE);
1864 return;
1865 }
1866
1867 /* Status must be Established. */
1868 if (peer->status != Established)
1869 {
1870 plog_err (peer->log,
1871 "%s [Error] Route refresh packet received under status %s",
1872 peer->host, LOOKUP (bgp_status_msg, peer->status));
1873 bgp_notify_send (peer, BGP_NOTIFY_FSM_ERR, 0);
1874 return;
1875 }
1876
1877 s = peer->ibuf;
1878
1879 /* Parse packet. */
1880 afi = stream_getw (s);
1881 reserved = stream_getc (s);
1882 safi = stream_getc (s);
1883
1884 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001885 zlog_debug ("%s rcvd REFRESH_REQ for afi/safi: %d/%d",
paul718e3742002-12-13 20:15:29 +00001886 peer->host, afi, safi);
1887
1888 /* Check AFI and SAFI. */
1889 if ((afi != AFI_IP && afi != AFI_IP6)
1890 || (safi != SAFI_UNICAST && safi != SAFI_MULTICAST
1891 && safi != BGP_SAFI_VPNV4))
1892 {
1893 if (BGP_DEBUG (normal, NORMAL))
1894 {
ajs6b514742004-12-08 21:03:23 +00001895 zlog_debug ("%s REFRESH_REQ for unrecognized afi/safi: %d/%d - ignored",
paul718e3742002-12-13 20:15:29 +00001896 peer->host, afi, safi);
1897 }
1898 return;
1899 }
1900
1901 /* Adjust safi code. */
1902 if (safi == BGP_SAFI_VPNV4)
1903 safi = SAFI_MPLS_VPN;
1904
1905 if (size != BGP_MSG_ROUTE_REFRESH_MIN_SIZE - BGP_HEADER_SIZE)
1906 {
1907 u_char *end;
1908 u_char when_to_refresh;
1909 u_char orf_type;
1910 u_int16_t orf_len;
1911
1912 if (size - (BGP_MSG_ROUTE_REFRESH_MIN_SIZE - BGP_HEADER_SIZE) < 5)
1913 {
1914 zlog_info ("%s ORF route refresh length error", peer->host);
1915 bgp_notify_send (peer, BGP_NOTIFY_CEASE, 0);
1916 return;
1917 }
1918
1919 when_to_refresh = stream_getc (s);
1920 end = stream_pnt (s) + (size - 5);
1921
1922 while (stream_pnt (s) < end)
1923 {
1924 orf_type = stream_getc (s);
1925 orf_len = stream_getw (s);
1926
1927 if (orf_type == ORF_TYPE_PREFIX
1928 || orf_type == ORF_TYPE_PREFIX_OLD)
1929 {
1930 u_char *p_pnt = stream_pnt (s);
1931 u_char *p_end = stream_pnt (s) + orf_len;
1932 struct orf_prefix orfp;
1933 u_char common = 0;
1934 u_int32_t seq;
1935 int psize;
1936 char name[BUFSIZ];
1937 char buf[BUFSIZ];
1938 int ret;
1939
1940 if (BGP_DEBUG (normal, NORMAL))
1941 {
ajs6b514742004-12-08 21:03:23 +00001942 zlog_debug ("%s rcvd Prefixlist ORF(%d) length %d",
paul718e3742002-12-13 20:15:29 +00001943 peer->host, orf_type, orf_len);
1944 }
1945
1946 /* ORF prefix-list name */
1947 sprintf (name, "%s.%d.%d", peer->host, afi, safi);
1948
1949 while (p_pnt < p_end)
1950 {
1951 memset (&orfp, 0, sizeof (struct orf_prefix));
1952 common = *p_pnt++;
1953 if (common & ORF_COMMON_PART_REMOVE_ALL)
1954 {
1955 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001956 zlog_debug ("%s rcvd Remove-All pfxlist ORF request", peer->host);
paul718e3742002-12-13 20:15:29 +00001957 prefix_bgp_orf_remove_all (name);
1958 break;
1959 }
1960 memcpy (&seq, p_pnt, sizeof (u_int32_t));
1961 p_pnt += sizeof (u_int32_t);
1962 orfp.seq = ntohl (seq);
1963 orfp.ge = *p_pnt++;
1964 orfp.le = *p_pnt++;
1965 orfp.p.prefixlen = *p_pnt++;
1966 orfp.p.family = afi2family (afi);
1967 psize = PSIZE (orfp.p.prefixlen);
1968 memcpy (&orfp.p.u.prefix, p_pnt, psize);
1969 p_pnt += psize;
1970
1971 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001972 zlog_debug ("%s rcvd %s %s seq %u %s/%d ge %d le %d",
paul718e3742002-12-13 20:15:29 +00001973 peer->host,
1974 (common & ORF_COMMON_PART_REMOVE ? "Remove" : "Add"),
1975 (common & ORF_COMMON_PART_DENY ? "deny" : "permit"),
1976 orfp.seq,
1977 inet_ntop (orfp.p.family, &orfp.p.u.prefix, buf, BUFSIZ),
1978 orfp.p.prefixlen, orfp.ge, orfp.le);
1979
1980 ret = prefix_bgp_orf_set (name, afi, &orfp,
1981 (common & ORF_COMMON_PART_DENY ? 0 : 1 ),
1982 (common & ORF_COMMON_PART_REMOVE ? 0 : 1));
1983
1984 if (ret != CMD_SUCCESS)
1985 {
1986 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001987 zlog_debug ("%s Received misformatted prefixlist ORF. Remove All pfxlist", peer->host);
paul718e3742002-12-13 20:15:29 +00001988 prefix_bgp_orf_remove_all (name);
1989 break;
1990 }
1991 }
1992 peer->orf_plist[afi][safi] =
1993 prefix_list_lookup (AFI_ORF_PREFIX, name);
1994 }
1995 stream_forward (s, orf_len);
1996 }
1997 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00001998 zlog_debug ("%s rcvd Refresh %s ORF request", peer->host,
paul718e3742002-12-13 20:15:29 +00001999 when_to_refresh == REFRESH_DEFER ? "Defer" : "Immediate");
2000 if (when_to_refresh == REFRESH_DEFER)
2001 return;
2002 }
2003
2004 /* First update is deferred until ORF or ROUTE-REFRESH is received */
2005 if (CHECK_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_ORF_WAIT_REFRESH))
2006 UNSET_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_ORF_WAIT_REFRESH);
2007
2008 /* Perform route refreshment to the peer */
2009 bgp_announce_route (peer, afi, safi);
2010}
2011
2012int
2013bgp_capability_msg_parse (struct peer *peer, u_char *pnt, bgp_size_t length)
2014{
2015 u_char *end;
2016 struct capability cap;
2017 u_char action;
2018 struct bgp *bgp;
2019 afi_t afi;
2020 safi_t safi;
2021
2022 bgp = peer->bgp;
2023 end = pnt + length;
2024
2025 while (pnt < end)
2026 {
2027 /* We need at least action, capability code and capability length. */
2028 if (pnt + 3 > end)
2029 {
2030 zlog_info ("%s Capability length error", peer->host);
2031 bgp_notify_send (peer, BGP_NOTIFY_CEASE, 0);
2032 return -1;
2033 }
2034
2035 action = *pnt;
2036
2037 /* Fetch structure to the byte stream. */
2038 memcpy (&cap, pnt + 1, sizeof (struct capability));
2039
2040 /* Action value check. */
2041 if (action != CAPABILITY_ACTION_SET
2042 && action != CAPABILITY_ACTION_UNSET)
2043 {
2044 zlog_info ("%s Capability Action Value error %d",
2045 peer->host, action);
2046 bgp_notify_send (peer, BGP_NOTIFY_CEASE, 0);
2047 return -1;
2048 }
2049
2050 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00002051 zlog_debug ("%s CAPABILITY has action: %d, code: %u, length %u",
paul718e3742002-12-13 20:15:29 +00002052 peer->host, action, cap.code, cap.length);
2053
2054 /* Capability length check. */
2055 if (pnt + (cap.length + 3) > end)
2056 {
2057 zlog_info ("%s Capability length error", peer->host);
2058 bgp_notify_send (peer, BGP_NOTIFY_CEASE, 0);
2059 return -1;
2060 }
2061
2062 /* We know MP Capability Code. */
2063 if (cap.code == CAPABILITY_CODE_MP)
2064 {
2065 afi = ntohs (cap.mpc.afi);
2066 safi = cap.mpc.safi;
2067
2068 /* Ignore capability when override-capability is set. */
2069 if (CHECK_FLAG (peer->flags, PEER_FLAG_OVERRIDE_CAPABILITY))
2070 continue;
2071
2072 /* Address family check. */
2073 if ((afi == AFI_IP
2074 || afi == AFI_IP6)
2075 && (safi == SAFI_UNICAST
2076 || safi == SAFI_MULTICAST
2077 || safi == BGP_SAFI_VPNV4))
2078 {
2079 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00002080 zlog_debug ("%s CAPABILITY has %s MP_EXT CAP for afi/safi: %u/%u",
paul718e3742002-12-13 20:15:29 +00002081 peer->host,
2082 action == CAPABILITY_ACTION_SET
2083 ? "Advertising" : "Removing",
2084 ntohs(cap.mpc.afi) , cap.mpc.safi);
2085
2086 /* Adjust safi code. */
2087 if (safi == BGP_SAFI_VPNV4)
2088 safi = SAFI_MPLS_VPN;
2089
2090 if (action == CAPABILITY_ACTION_SET)
2091 {
2092 peer->afc_recv[afi][safi] = 1;
2093 if (peer->afc[afi][safi])
2094 {
2095 peer->afc_nego[afi][safi] = 1;
2096 bgp_announce_route (peer, afi, safi);
2097 }
2098 }
2099 else
2100 {
2101 peer->afc_recv[afi][safi] = 0;
2102 peer->afc_nego[afi][safi] = 0;
2103
2104 if (peer_active_nego (peer))
2105 bgp_clear_route (peer, afi, safi);
2106 else
2107 BGP_EVENT_ADD (peer, BGP_Stop);
2108 }
2109 }
2110 }
paul718e3742002-12-13 20:15:29 +00002111 else
2112 {
2113 zlog_warn ("%s unrecognized capability code: %d - ignored",
2114 peer->host, cap.code);
2115 }
2116 pnt += cap.length + 3;
2117 }
2118 return 0;
2119}
2120
2121/* Dynamic Capability is received. */
2122void
2123bgp_capability_receive (struct peer *peer, bgp_size_t size)
2124{
2125 u_char *pnt;
2126 int ret;
2127
2128 /* Fetch pointer. */
2129 pnt = stream_pnt (peer->ibuf);
2130
2131 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00002132 zlog_debug ("%s rcv CAPABILITY", peer->host);
paul718e3742002-12-13 20:15:29 +00002133
2134 /* If peer does not have the capability, send notification. */
2135 if (! CHECK_FLAG (peer->cap, PEER_CAP_DYNAMIC_ADV))
2136 {
2137 plog_err (peer->log, "%s [Error] BGP dynamic capability is not enabled",
2138 peer->host);
2139 bgp_notify_send (peer,
2140 BGP_NOTIFY_HEADER_ERR,
2141 BGP_NOTIFY_HEADER_BAD_MESTYPE);
2142 return;
2143 }
2144
2145 /* Status must be Established. */
2146 if (peer->status != Established)
2147 {
2148 plog_err (peer->log,
2149 "%s [Error] Dynamic capability packet received under status %s", peer->host, LOOKUP (bgp_status_msg, peer->status));
2150 bgp_notify_send (peer, BGP_NOTIFY_FSM_ERR, 0);
2151 return;
2152 }
2153
2154 /* Parse packet. */
2155 ret = bgp_capability_msg_parse (peer, pnt, size);
2156}
2157
2158/* BGP read utility function. */
2159int
2160bgp_read_packet (struct peer *peer)
2161{
2162 int nbytes;
2163 int readsize;
2164
2165 readsize = peer->packet_size - peer->ibuf->putp;
2166
2167 /* If size is zero then return. */
2168 if (! readsize)
2169 return 0;
2170
2171 /* Read packet from fd. */
pauleb821182004-05-01 08:44:08 +00002172 nbytes = stream_read_unblock (peer->ibuf, peer->fd, readsize);
paul718e3742002-12-13 20:15:29 +00002173
2174 /* If read byte is smaller than zero then error occured. */
2175 if (nbytes < 0)
2176 {
2177 if (errno == EAGAIN)
2178 return -1;
2179
2180 plog_err (peer->log, "%s [Error] bgp_read_packet error: %s",
ajs6099b3b2004-11-20 02:06:59 +00002181 peer->host, safe_strerror (errno));
hasso93406d82005-02-02 14:40:33 +00002182
2183 if (peer->status == Established)
2184 {
2185 if (CHECK_FLAG (peer->sflags, PEER_STATUS_NSF_MODE))
2186 {
2187 peer->last_reset = PEER_DOWN_NSF_CLOSE_SESSION;
2188 SET_FLAG (peer->sflags, PEER_STATUS_NSF_WAIT);
2189 }
2190 else
2191 peer->last_reset = PEER_DOWN_CLOSE_SESSION;
2192 }
2193
paul718e3742002-12-13 20:15:29 +00002194 BGP_EVENT_ADD (peer, TCP_fatal_error);
2195 return -1;
2196 }
2197
2198 /* When read byte is zero : clear bgp peer and return */
2199 if (nbytes == 0)
2200 {
2201 if (BGP_DEBUG (events, EVENTS))
ajs6b514742004-12-08 21:03:23 +00002202 plog_debug (peer->log, "%s [Event] BGP connection closed fd %d",
pauleb821182004-05-01 08:44:08 +00002203 peer->host, peer->fd);
hassoe0701b72004-05-20 09:19:34 +00002204
2205 if (peer->status == Established)
hasso93406d82005-02-02 14:40:33 +00002206 {
2207 if (CHECK_FLAG (peer->sflags, PEER_STATUS_NSF_MODE))
2208 {
2209 peer->last_reset = PEER_DOWN_NSF_CLOSE_SESSION;
2210 SET_FLAG (peer->sflags, PEER_STATUS_NSF_WAIT);
2211 }
2212 else
2213 peer->last_reset = PEER_DOWN_CLOSE_SESSION;
2214 }
hassoe0701b72004-05-20 09:19:34 +00002215
paul718e3742002-12-13 20:15:29 +00002216 BGP_EVENT_ADD (peer, TCP_connection_closed);
2217 return -1;
2218 }
2219
2220 /* We read partial packet. */
2221 if (peer->ibuf->putp != peer->packet_size)
2222 return -1;
2223
2224 return 0;
2225}
2226
2227/* Marker check. */
2228int
2229bgp_marker_all_one (struct stream *s, int length)
2230{
2231 int i;
2232
2233 for (i = 0; i < length; i++)
2234 if (s->data[i] != 0xff)
2235 return 0;
2236
2237 return 1;
2238}
2239
2240/* Starting point of packet process function. */
2241int
2242bgp_read (struct thread *thread)
2243{
2244 int ret;
2245 u_char type = 0;
2246 struct peer *peer;
2247 bgp_size_t size;
2248 char notify_data_length[2];
2249
2250 /* Yes first of all get peer pointer. */
2251 peer = THREAD_ARG (thread);
2252 peer->t_read = NULL;
2253
2254 /* For non-blocking IO check. */
2255 if (peer->status == Connect)
2256 {
2257 bgp_connect_check (peer);
2258 goto done;
2259 }
2260 else
2261 {
pauleb821182004-05-01 08:44:08 +00002262 if (peer->fd < 0)
paul718e3742002-12-13 20:15:29 +00002263 {
pauleb821182004-05-01 08:44:08 +00002264 zlog_err ("bgp_read peer's fd is negative value %d", peer->fd);
paul718e3742002-12-13 20:15:29 +00002265 return -1;
2266 }
pauleb821182004-05-01 08:44:08 +00002267 BGP_READ_ON (peer->t_read, bgp_read, peer->fd);
paul718e3742002-12-13 20:15:29 +00002268 }
2269
2270 /* Read packet header to determine type of the packet */
2271 if (peer->packet_size == 0)
2272 peer->packet_size = BGP_HEADER_SIZE;
2273
2274 if (peer->ibuf->putp < BGP_HEADER_SIZE)
2275 {
2276 ret = bgp_read_packet (peer);
2277
2278 /* Header read error or partial read packet. */
2279 if (ret < 0)
2280 goto done;
2281
2282 /* Get size and type. */
2283 stream_forward (peer->ibuf, BGP_MARKER_SIZE);
2284 memcpy (notify_data_length, stream_pnt (peer->ibuf), 2);
2285 size = stream_getw (peer->ibuf);
2286 type = stream_getc (peer->ibuf);
2287
2288 if (BGP_DEBUG (normal, NORMAL) && type != 2 && type != 0)
ajs6b514742004-12-08 21:03:23 +00002289 zlog_debug ("%s rcv message type %d, length (excl. header) %d",
paul718e3742002-12-13 20:15:29 +00002290 peer->host, type, size - BGP_HEADER_SIZE);
2291
2292 /* Marker check */
paulf5ba3872004-07-09 12:11:31 +00002293 if (((type == BGP_MSG_OPEN) || (type == BGP_MSG_KEEPALIVE))
paul718e3742002-12-13 20:15:29 +00002294 && ! bgp_marker_all_one (peer->ibuf, BGP_MARKER_SIZE))
2295 {
2296 bgp_notify_send (peer,
2297 BGP_NOTIFY_HEADER_ERR,
2298 BGP_NOTIFY_HEADER_NOT_SYNC);
2299 goto done;
2300 }
2301
2302 /* BGP type check. */
2303 if (type != BGP_MSG_OPEN && type != BGP_MSG_UPDATE
2304 && type != BGP_MSG_NOTIFY && type != BGP_MSG_KEEPALIVE
2305 && type != BGP_MSG_ROUTE_REFRESH_NEW
2306 && type != BGP_MSG_ROUTE_REFRESH_OLD
2307 && type != BGP_MSG_CAPABILITY)
2308 {
2309 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00002310 plog_debug (peer->log,
paul718e3742002-12-13 20:15:29 +00002311 "%s unknown message type 0x%02x",
2312 peer->host, type);
2313 bgp_notify_send_with_data (peer,
2314 BGP_NOTIFY_HEADER_ERR,
2315 BGP_NOTIFY_HEADER_BAD_MESTYPE,
2316 &type, 1);
2317 goto done;
2318 }
2319 /* Mimimum packet length check. */
2320 if ((size < BGP_HEADER_SIZE)
2321 || (size > BGP_MAX_PACKET_SIZE)
2322 || (type == BGP_MSG_OPEN && size < BGP_MSG_OPEN_MIN_SIZE)
2323 || (type == BGP_MSG_UPDATE && size < BGP_MSG_UPDATE_MIN_SIZE)
2324 || (type == BGP_MSG_NOTIFY && size < BGP_MSG_NOTIFY_MIN_SIZE)
2325 || (type == BGP_MSG_KEEPALIVE && size != BGP_MSG_KEEPALIVE_MIN_SIZE)
2326 || (type == BGP_MSG_ROUTE_REFRESH_NEW && size < BGP_MSG_ROUTE_REFRESH_MIN_SIZE)
2327 || (type == BGP_MSG_ROUTE_REFRESH_OLD && size < BGP_MSG_ROUTE_REFRESH_MIN_SIZE)
2328 || (type == BGP_MSG_CAPABILITY && size < BGP_MSG_CAPABILITY_MIN_SIZE))
2329 {
2330 if (BGP_DEBUG (normal, NORMAL))
ajs6b514742004-12-08 21:03:23 +00002331 plog_debug (peer->log,
paul718e3742002-12-13 20:15:29 +00002332 "%s bad message length - %d for %s",
2333 peer->host, size,
2334 type == 128 ? "ROUTE-REFRESH" :
2335 bgp_type_str[(int) type]);
2336 bgp_notify_send_with_data (peer,
2337 BGP_NOTIFY_HEADER_ERR,
2338 BGP_NOTIFY_HEADER_BAD_MESLEN,
hassoc9e52be2004-09-26 16:09:34 +00002339 (u_char *) notify_data_length, 2);
paul718e3742002-12-13 20:15:29 +00002340 goto done;
2341 }
2342
2343 /* Adjust size to message length. */
2344 peer->packet_size = size;
2345 }
2346
2347 ret = bgp_read_packet (peer);
2348 if (ret < 0)
2349 goto done;
2350
2351 /* Get size and type again. */
2352 size = stream_getw_from (peer->ibuf, BGP_MARKER_SIZE);
2353 type = stream_getc_from (peer->ibuf, BGP_MARKER_SIZE + 2);
2354
2355 /* BGP packet dump function. */
2356 bgp_dump_packet (peer, type, peer->ibuf);
2357
2358 size = (peer->packet_size - BGP_HEADER_SIZE);
2359
2360 /* Read rest of the packet and call each sort of packet routine */
2361 switch (type)
2362 {
2363 case BGP_MSG_OPEN:
2364 peer->open_in++;
paulf5ba3872004-07-09 12:11:31 +00002365 bgp_open_receive (peer, size); /* XXX return value ignored! */
paul718e3742002-12-13 20:15:29 +00002366 break;
2367 case BGP_MSG_UPDATE:
2368 peer->readtime = time(NULL); /* Last read timer reset */
2369 bgp_update_receive (peer, size);
2370 break;
2371 case BGP_MSG_NOTIFY:
2372 bgp_notify_receive (peer, size);
2373 break;
2374 case BGP_MSG_KEEPALIVE:
2375 peer->readtime = time(NULL); /* Last read timer reset */
2376 bgp_keepalive_receive (peer, size);
2377 break;
2378 case BGP_MSG_ROUTE_REFRESH_NEW:
2379 case BGP_MSG_ROUTE_REFRESH_OLD:
2380 peer->refresh_in++;
2381 bgp_route_refresh_receive (peer, size);
2382 break;
2383 case BGP_MSG_CAPABILITY:
2384 peer->dynamic_cap_in++;
2385 bgp_capability_receive (peer, size);
2386 break;
2387 }
2388
2389 /* Clear input buffer. */
2390 peer->packet_size = 0;
2391 if (peer->ibuf)
2392 stream_reset (peer->ibuf);
2393
2394 done:
2395 if (CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
2396 {
2397 if (BGP_DEBUG (events, EVENTS))
ajs6b514742004-12-08 21:03:23 +00002398 zlog_debug ("%s [Event] Accepting BGP peer delete", peer->host);
paul718e3742002-12-13 20:15:29 +00002399 peer_delete (peer);
2400 }
2401 return 0;
2402}