]> git.sommitrealweird.co.uk Git - quagga-debian.git/blob - bgpd/bgpd.c
6aeecb13dd3dcbace0f3804f1a02edb670c896a4
[quagga-debian.git] / bgpd / bgpd.c
1 /* BGP-4, BGP-4+ daemon program
2    Copyright (C) 1996, 97, 98, 99, 2000 Kunihiro Ishiguro
3
4 This file is part of GNU Zebra.
5
6 GNU Zebra is free software; you can redistribute it and/or modify it
7 under the terms of the GNU General Public License as published by the
8 Free Software Foundation; either version 2, or (at your option) any
9 later version.
10
11 GNU Zebra is distributed in the hope that it will be useful, but
12 WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
14 General Public License for more details.
15
16 You should have received a copy of the GNU General Public License
17 along with GNU Zebra; see the file COPYING.  If not, write to the Free
18 Software Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
19 02111-1307, USA.  */
20
21 #include <zebra.h>
22
23 #include "prefix.h"
24 #include "thread.h"
25 #include "buffer.h"
26 #include "stream.h"
27 #include "command.h"
28 #include "sockunion.h"
29 #include "sockopt.h"
30 #include "network.h"
31 #include "memory.h"
32 #include "filter.h"
33 #include "routemap.h"
34 #include "str.h"
35 #include "log.h"
36 #include "plist.h"
37 #include "linklist.h"
38 #include "workqueue.h"
39 #include "table.h"
40
41 #include "bgpd/bgpd.h"
42 #include "bgpd/bgp_table.h"
43 #include "bgpd/bgp_aspath.h"
44 #include "bgpd/bgp_route.h"
45 #include "bgpd/bgp_dump.h"
46 #include "bgpd/bgp_debug.h"
47 #include "bgpd/bgp_community.h"
48 #include "bgpd/bgp_attr.h"
49 #include "bgpd/bgp_regex.h"
50 #include "bgpd/bgp_clist.h"
51 #include "bgpd/bgp_fsm.h"
52 #include "bgpd/bgp_packet.h"
53 #include "bgpd/bgp_zebra.h"
54 #include "bgpd/bgp_open.h"
55 #include "bgpd/bgp_filter.h"
56 #include "bgpd/bgp_nexthop.h"
57 #include "bgpd/bgp_damp.h"
58 #include "bgpd/bgp_mplsvpn.h"
59 #include "bgpd/bgp_encap.h"
60 #include "bgpd/bgp_advertise.h"
61 #include "bgpd/bgp_network.h"
62 #include "bgpd/bgp_vty.h"
63 #include "bgpd/bgp_mpath.h"
64 #include "bgpd/bgp_nht.h"
65 #ifdef HAVE_SNMP
66 #include "bgpd/bgp_snmp.h"
67 #endif /* HAVE_SNMP */
68
69 /* BGP process wide configuration.  */
70 static struct bgp_master bgp_master;
71
72 extern struct in_addr router_id_zebra;
73
74 /* BGP process wide configuration pointer to export.  */
75 struct bgp_master *bm;
76
77 /* BGP community-list.  */
78 struct community_list_handler *bgp_clist;
79
80 /* BGP global flag manipulation.  */
81 int
82 bgp_option_set (int flag)
83 {
84   switch (flag)
85     {
86     case BGP_OPT_NO_FIB:
87     case BGP_OPT_MULTIPLE_INSTANCE:
88     case BGP_OPT_CONFIG_CISCO:
89     case BGP_OPT_NO_LISTEN:
90       SET_FLAG (bm->options, flag);
91       break;
92     default:
93       return BGP_ERR_INVALID_FLAG;
94     }
95   return 0;
96 }
97
98 int
99 bgp_option_unset (int flag)
100 {
101   switch (flag)
102     {
103     case BGP_OPT_MULTIPLE_INSTANCE:
104       if (listcount (bm->bgp) > 1)
105         return BGP_ERR_MULTIPLE_INSTANCE_USED;
106       /* Fall through.  */
107     case BGP_OPT_NO_FIB:
108     case BGP_OPT_CONFIG_CISCO:
109       UNSET_FLAG (bm->options, flag);
110       break;
111     default:
112       return BGP_ERR_INVALID_FLAG;
113     }
114   return 0;
115 }
116
117 int
118 bgp_option_check (int flag)
119 {
120   return CHECK_FLAG (bm->options, flag);
121 }
122
123 /* BGP flag manipulation.  */
124 int
125 bgp_flag_set (struct bgp *bgp, int flag)
126 {
127   SET_FLAG (bgp->flags, flag);
128   return 0;
129 }
130
131 int
132 bgp_flag_unset (struct bgp *bgp, int flag)
133 {
134   UNSET_FLAG (bgp->flags, flag);
135   return 0;
136 }
137
138 int
139 bgp_flag_check (struct bgp *bgp, int flag)
140 {
141   return CHECK_FLAG (bgp->flags, flag);
142 }
143
144 /* Internal function to set BGP structure configureation flag.  */
145 static void
146 bgp_config_set (struct bgp *bgp, int config)
147 {
148   SET_FLAG (bgp->config, config);
149 }
150
151 static void
152 bgp_config_unset (struct bgp *bgp, int config)
153 {
154   UNSET_FLAG (bgp->config, config);
155 }
156
157 static int
158 bgp_config_check (struct bgp *bgp, int config)
159 {
160   return CHECK_FLAG (bgp->config, config);
161 }
162
163 /* Set BGP router identifier. */
164 static int
165 bgp_router_id_set (struct bgp *bgp, struct in_addr *id)
166 {
167   struct peer *peer;
168   struct listnode *node, *nnode;
169
170   if (bgp_config_check (bgp, BGP_CONFIG_ROUTER_ID)
171       && IPV4_ADDR_SAME (&bgp->router_id, id))
172     return 0;
173
174   IPV4_ADDR_COPY (&bgp->router_id, id);
175   bgp_config_set (bgp, BGP_CONFIG_ROUTER_ID);
176
177   /* Set all peer's local identifier with this value. */
178   for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
179     {
180       IPV4_ADDR_COPY (&peer->local_id, id);
181
182       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
183        {
184          peer->last_reset = PEER_DOWN_RID_CHANGE;
185          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
186                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
187        }
188     }
189   return 0;
190 }
191
192 void
193 bgp_router_id_zebra_bump (void)
194 {
195   struct listnode *node, *nnode;
196   struct bgp *bgp;
197
198   for (ALL_LIST_ELEMENTS (bm->bgp, node, nnode, bgp))
199     {
200       if (!bgp->router_id_static.s_addr)
201         bgp_router_id_set (bgp, &router_id_zebra);
202     }
203 }
204
205 int
206 bgp_router_id_static_set (struct bgp *bgp, struct in_addr id)
207 {
208   bgp->router_id_static = id;
209   bgp_router_id_set (bgp, id.s_addr ? &id : &router_id_zebra);
210   return 0;
211 }
212
213 /* BGP's cluster-id control. */
214 int
215 bgp_cluster_id_set (struct bgp *bgp, struct in_addr *cluster_id)
216 {
217   struct peer *peer;
218   struct listnode *node, *nnode;
219
220   if (bgp_config_check (bgp, BGP_CONFIG_CLUSTER_ID)
221       && IPV4_ADDR_SAME (&bgp->cluster_id, cluster_id))
222     return 0;
223
224   IPV4_ADDR_COPY (&bgp->cluster_id, cluster_id);
225   bgp_config_set (bgp, BGP_CONFIG_CLUSTER_ID);
226
227   /* Clear all IBGP peer. */
228   for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
229     {
230       if (peer->sort != BGP_PEER_IBGP)
231         continue;
232
233       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
234        {
235          peer->last_reset = PEER_DOWN_CLID_CHANGE;
236          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
237                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
238        }
239     }
240   return 0;
241 }
242
243 int
244 bgp_cluster_id_unset (struct bgp *bgp)
245 {
246   struct peer *peer;
247   struct listnode *node, *nnode;
248
249   if (! bgp_config_check (bgp, BGP_CONFIG_CLUSTER_ID))
250     return 0;
251
252   bgp->cluster_id.s_addr = 0;
253   bgp_config_unset (bgp, BGP_CONFIG_CLUSTER_ID);
254
255   /* Clear all IBGP peer. */
256   for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
257     {
258       if (peer->sort != BGP_PEER_IBGP)
259         continue;
260
261       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
262        {
263          peer->last_reset = PEER_DOWN_CLID_CHANGE;
264          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
265                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
266        }
267     }
268   return 0;
269 }
270
271 /* time_t value that is monotonicly increasing
272  * and uneffected by adjustments to system clock
273  */
274 time_t bgp_clock (void)
275 {
276   struct timeval tv;
277
278   quagga_gettime(QUAGGA_CLK_MONOTONIC, &tv);
279   return tv.tv_sec;
280 }
281
282 /* BGP timer configuration.  */
283 int
284 bgp_timers_set (struct bgp *bgp, u_int32_t keepalive, u_int32_t holdtime)
285 {
286   bgp->default_keepalive = (keepalive < holdtime / 3 
287                             ? keepalive : holdtime / 3);
288   bgp->default_holdtime = holdtime;
289
290   return 0;
291 }
292
293 int
294 bgp_timers_unset (struct bgp *bgp)
295 {
296   bgp->default_keepalive = BGP_DEFAULT_KEEPALIVE;
297   bgp->default_holdtime = BGP_DEFAULT_HOLDTIME;
298
299   return 0;
300 }
301
302 /* BGP confederation configuration.  */
303 int
304 bgp_confederation_id_set (struct bgp *bgp, as_t as)
305 {
306   struct peer *peer;
307   struct listnode *node, *nnode;
308   int already_confed;
309
310   if (as == 0)
311     return BGP_ERR_INVALID_AS;
312
313   /* Remember - were we doing confederation before? */
314   already_confed = bgp_config_check (bgp, BGP_CONFIG_CONFEDERATION);
315   bgp->confed_id = as;
316   bgp_config_set (bgp, BGP_CONFIG_CONFEDERATION);
317
318   /* If we were doing confederation already, this is just an external
319      AS change.  Just Reset EBGP sessions, not CONFED sessions.  If we
320      were not doing confederation before, reset all EBGP sessions.  */
321   for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
322     {
323       /* We're looking for peers who's AS is not local or part of our
324          confederation.  */
325       if (already_confed)
326         {
327           if (peer_sort (peer) == BGP_PEER_EBGP)
328             {
329               peer->local_as = as;
330               if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
331                {
332                  peer->last_reset = PEER_DOWN_CONFED_ID_CHANGE;
333                  bgp_notify_send (peer, BGP_NOTIFY_CEASE,
334                               BGP_NOTIFY_CEASE_CONFIG_CHANGE);
335                }
336
337               else
338                 BGP_EVENT_ADD (peer, BGP_Stop);
339             }
340         }
341       else
342         {
343           /* Not doign confederation before, so reset every non-local
344              session */
345           if (peer_sort (peer) != BGP_PEER_IBGP)
346             {
347               /* Reset the local_as to be our EBGP one */
348               if (peer_sort (peer) == BGP_PEER_EBGP)
349                 peer->local_as = as;
350               if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
351                {
352                  peer->last_reset = PEER_DOWN_CONFED_ID_CHANGE;
353                  bgp_notify_send (peer, BGP_NOTIFY_CEASE,
354                               BGP_NOTIFY_CEASE_CONFIG_CHANGE);
355                }
356               else
357                 BGP_EVENT_ADD (peer, BGP_Stop);
358             }
359         }
360     }
361   return 0;
362 }
363
364 int
365 bgp_confederation_id_unset (struct bgp *bgp)
366 {
367   struct peer *peer;
368   struct listnode *node, *nnode;
369
370   bgp->confed_id = 0;
371   bgp_config_unset (bgp, BGP_CONFIG_CONFEDERATION);
372       
373   for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
374     {
375       /* We're looking for peers who's AS is not local */
376       if (peer_sort (peer) != BGP_PEER_IBGP)
377         {
378           peer->local_as = bgp->as;
379           if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
380            {
381              peer->last_reset = PEER_DOWN_CONFED_ID_CHANGE;
382              bgp_notify_send (peer, BGP_NOTIFY_CEASE,
383                               BGP_NOTIFY_CEASE_CONFIG_CHANGE);
384            }
385
386           else
387             BGP_EVENT_ADD (peer, BGP_Stop);
388         }
389     }
390   return 0;
391 }
392
393 /* Is an AS part of the confed or not? */
394 int
395 bgp_confederation_peers_check (struct bgp *bgp, as_t as)
396 {
397   int i;
398
399   if (! bgp)
400     return 0;
401
402   for (i = 0; i < bgp->confed_peers_cnt; i++)
403     if (bgp->confed_peers[i] == as)
404       return 1;
405   
406   return 0;
407 }
408
409 /* Add an AS to the confederation set.  */
410 int
411 bgp_confederation_peers_add (struct bgp *bgp, as_t as)
412 {
413   struct peer *peer;
414   struct listnode *node, *nnode;
415
416   if (! bgp)
417     return BGP_ERR_INVALID_BGP;
418
419   if (bgp->as == as)
420     return BGP_ERR_INVALID_AS;
421
422   if (bgp_confederation_peers_check (bgp, as))
423     return -1;
424
425   if (bgp->confed_peers)
426     bgp->confed_peers = XREALLOC (MTYPE_BGP_CONFED_LIST, 
427                                   bgp->confed_peers,
428                                   (bgp->confed_peers_cnt + 1) * sizeof (as_t));
429   else
430     bgp->confed_peers = XMALLOC (MTYPE_BGP_CONFED_LIST, 
431                                  (bgp->confed_peers_cnt + 1) * sizeof (as_t));
432
433   bgp->confed_peers[bgp->confed_peers_cnt] = as;
434   bgp->confed_peers_cnt++;
435
436   if (bgp_config_check (bgp, BGP_CONFIG_CONFEDERATION))
437     {
438       for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
439         {
440           if (peer->as == as)
441             {
442               peer->local_as = bgp->as;
443               if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
444                {
445                  peer->last_reset = PEER_DOWN_CONFED_PEER_CHANGE;
446                  bgp_notify_send (peer, BGP_NOTIFY_CEASE,
447                                   BGP_NOTIFY_CEASE_CONFIG_CHANGE);
448                }
449               else
450                 BGP_EVENT_ADD (peer, BGP_Stop);
451             }
452         }
453     }
454   return 0;
455 }
456
457 /* Delete an AS from the confederation set.  */
458 int
459 bgp_confederation_peers_remove (struct bgp *bgp, as_t as)
460 {
461   int i;
462   int j;
463   struct peer *peer;
464   struct listnode *node, *nnode;
465
466   if (! bgp)
467     return -1;
468
469   if (! bgp_confederation_peers_check (bgp, as))
470     return -1;
471
472   for (i = 0; i < bgp->confed_peers_cnt; i++)
473     if (bgp->confed_peers[i] == as)
474       for(j = i + 1; j < bgp->confed_peers_cnt; j++)
475         bgp->confed_peers[j - 1] = bgp->confed_peers[j];
476
477   bgp->confed_peers_cnt--;
478
479   if (bgp->confed_peers_cnt == 0)
480     {
481       if (bgp->confed_peers)
482         XFREE (MTYPE_BGP_CONFED_LIST, bgp->confed_peers);
483       bgp->confed_peers = NULL;
484     }
485   else
486     bgp->confed_peers = XREALLOC (MTYPE_BGP_CONFED_LIST,
487                                   bgp->confed_peers,
488                                   bgp->confed_peers_cnt * sizeof (as_t));
489
490   /* Now reset any peer who's remote AS has just been removed from the
491      CONFED */
492   if (bgp_config_check (bgp, BGP_CONFIG_CONFEDERATION))
493     {
494       for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
495         {
496           if (peer->as == as)
497             {
498               peer->local_as = bgp->confed_id;
499               if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
500                {
501                  peer->last_reset = PEER_DOWN_CONFED_PEER_CHANGE;
502                  bgp_notify_send (peer, BGP_NOTIFY_CEASE,
503                                   BGP_NOTIFY_CEASE_CONFIG_CHANGE);
504                }
505               else
506                 BGP_EVENT_ADD (peer, BGP_Stop);
507             }
508         }
509     }
510
511   return 0;
512 }
513
514 /* Local preference configuration.  */
515 int
516 bgp_default_local_preference_set (struct bgp *bgp, u_int32_t local_pref)
517 {
518   if (! bgp)
519     return -1;
520
521   bgp->default_local_pref = local_pref;
522
523   return 0;
524 }
525
526 int
527 bgp_default_local_preference_unset (struct bgp *bgp)
528 {
529   if (! bgp)
530     return -1;
531
532   bgp->default_local_pref = BGP_DEFAULT_LOCAL_PREF;
533
534   return 0;
535 }
536
537 /* If peer is RSERVER_CLIENT in at least one address family and is not member
538     of a peer_group for that family, return 1.
539     Used to check wether the peer is included in list bgp->rsclient. */
540 int
541 peer_rsclient_active (struct peer *peer)
542 {
543   int i;
544   int j;
545
546   for (i=AFI_IP; i < AFI_MAX; i++)
547     for (j=SAFI_UNICAST; j < SAFI_MAX; j++)
548       if (CHECK_FLAG(peer->af_flags[i][j], PEER_FLAG_RSERVER_CLIENT)
549             && ! peer->af_group[i][j])
550         return 1;
551   return 0;
552 }
553
554 /* Peer comparison function for sorting.  */
555 static int
556 peer_cmp (struct peer *p1, struct peer *p2)
557 {
558   return sockunion_cmp (&p1->su, &p2->su);
559 }
560
561 int
562 peer_af_flag_check (struct peer *peer, afi_t afi, safi_t safi, u_int32_t flag)
563 {
564   return CHECK_FLAG (peer->af_flags[afi][safi], flag);
565 }
566
567 /* Reset all address family specific configuration.  */
568 static void
569 peer_af_flag_reset (struct peer *peer, afi_t afi, safi_t safi)
570 {
571   int i;
572   struct bgp_filter *filter;
573   char orf_name[BUFSIZ];
574
575   filter = &peer->filter[afi][safi];
576
577   /* Clear neighbor filter and route-map */
578   for (i = FILTER_IN; i < FILTER_MAX; i++)
579     {
580       if (filter->dlist[i].name)
581         {
582           free (filter->dlist[i].name);
583           filter->dlist[i].name = NULL;
584         }
585       if (filter->plist[i].name)
586         {
587           free (filter->plist[i].name);
588           filter->plist[i].name = NULL; 
589         }
590       if (filter->aslist[i].name)
591         {
592           free (filter->aslist[i].name);
593           filter->aslist[i].name = NULL;
594         }
595    }
596  for (i = RMAP_IN; i < RMAP_MAX; i++)
597        {
598       if (filter->map[i].name)
599         {
600           free (filter->map[i].name);
601           filter->map[i].name = NULL;
602         }
603     }
604
605   /* Clear unsuppress map.  */
606   if (filter->usmap.name)
607     free (filter->usmap.name);
608   filter->usmap.name = NULL;
609   filter->usmap.map = NULL;
610
611   /* Clear neighbor's all address family flags.  */
612   peer->af_flags[afi][safi] = 0;
613
614   /* Clear neighbor's all address family sflags. */
615   peer->af_sflags[afi][safi] = 0;
616
617   /* Clear neighbor's all address family capabilities. */
618   peer->af_cap[afi][safi] = 0;
619
620   /* Clear ORF info */
621   peer->orf_plist[afi][safi] = NULL;
622   sprintf (orf_name, "%s.%d.%d", peer->host, afi, safi);
623   prefix_bgp_orf_remove_all (afi, orf_name);
624
625   /* Set default neighbor send-community.  */
626   if (! bgp_option_check (BGP_OPT_CONFIG_CISCO))
627     {
628       SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SEND_COMMUNITY);
629       SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SEND_EXT_COMMUNITY);
630       SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SEND_LARGE_COMMUNITY);
631     }
632
633   /* Clear neighbor default_originate_rmap */
634   if (peer->default_rmap[afi][safi].name)
635     free (peer->default_rmap[afi][safi].name);
636   peer->default_rmap[afi][safi].name = NULL;
637   peer->default_rmap[afi][safi].map = NULL;
638
639   /* Clear neighbor maximum-prefix */
640   peer->pmax[afi][safi] = 0;
641   peer->pmax_threshold[afi][safi] = MAXIMUM_PREFIX_THRESHOLD_DEFAULT;
642 }
643
644 /* peer global config reset */
645 static void
646 peer_global_config_reset (struct peer *peer)
647 {
648   peer->weight = 0;
649   peer->change_local_as = 0;
650   peer->ttl = 0;
651   peer->gtsm_hops = 0;
652   if (peer->update_source)
653     {
654       sockunion_free (peer->update_source);
655       peer->update_source = NULL;
656     }
657   if (peer->update_if)
658     {
659       XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
660       peer->update_if = NULL;
661     }
662
663   if (peer_sort (peer) == BGP_PEER_IBGP)
664     peer->v_routeadv = BGP_DEFAULT_IBGP_ROUTEADV;
665   else
666     peer->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
667
668   peer->flags = 0;
669   peer->config = 0;
670   peer->holdtime = 0;
671   peer->keepalive = 0;
672   peer->connect = 0;
673   peer->v_connect = BGP_DEFAULT_CONNECT_RETRY;
674 }
675
676 /* Check peer's AS number and determines if this peer is IBGP or EBGP */
677 static bgp_peer_sort_t
678 peer_calc_sort (struct peer *peer)
679 {
680   struct bgp *bgp;
681
682   bgp = peer->bgp;
683
684   /* Peer-group */
685   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
686     {
687       if (peer->as)
688         return (bgp->as == peer->as ? BGP_PEER_IBGP : BGP_PEER_EBGP);
689       else
690         {
691           struct peer *peer1;
692           peer1 = listnode_head (peer->group->peer);
693           if (peer1)
694             return (peer1->local_as == peer1->as 
695                     ? BGP_PEER_IBGP : BGP_PEER_EBGP);
696         } 
697       return BGP_PEER_INTERNAL;
698     }
699
700   /* Normal peer */
701   if (bgp && CHECK_FLAG (bgp->config, BGP_CONFIG_CONFEDERATION))
702     {
703       if (peer->local_as == 0)
704         return BGP_PEER_INTERNAL;
705
706       if (peer->local_as == peer->as)
707         {
708           if (peer->local_as == bgp->confed_id)
709             return BGP_PEER_EBGP;
710           else
711             return BGP_PEER_IBGP;
712         }
713
714       if (bgp_confederation_peers_check (bgp, peer->as))
715         return BGP_PEER_CONFED;
716
717       return BGP_PEER_EBGP;
718     }
719   else
720     {
721       return (peer->local_as == 0
722               ? BGP_PEER_INTERNAL : peer->local_as == peer->as
723               ? BGP_PEER_IBGP : BGP_PEER_EBGP);
724     }
725 }
726
727 /* Calculate and cache the peer "sort" */
728 bgp_peer_sort_t
729 peer_sort (struct peer *peer)
730 {
731   peer->sort = peer_calc_sort (peer);
732   return peer->sort;
733 }
734
735 static void
736 peer_free (struct peer *peer)
737 {
738   assert (peer->status == Deleted);
739
740   /* this /ought/ to have been done already through bgp_stop earlier,
741    * but just to be sure.. 
742    */
743   bgp_timer_set (peer);
744   BGP_READ_OFF (peer->t_read);
745   BGP_WRITE_OFF (peer->t_write);
746   BGP_EVENT_FLUSH (peer);
747   
748   if (peer->desc)
749     {
750       XFREE (MTYPE_PEER_DESC, peer->desc);
751       peer->desc = NULL;
752     }
753   
754   /* Free allocated host character. */
755   if (peer->host)
756     {
757       XFREE (MTYPE_BGP_PEER_HOST, peer->host);
758       peer->host = NULL;
759     }
760
761   /* Update source configuration.  */
762   if (peer->update_source)
763     {
764       sockunion_free (peer->update_source);
765       peer->update_source = NULL;
766     }
767   
768   if (peer->update_if)
769     {
770       XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
771       peer->update_if = NULL;
772     }
773     
774   if (peer->clear_node_queue)
775     {
776       work_queue_free(peer->clear_node_queue);
777       peer->clear_node_queue = NULL;
778     }
779   
780   if (peer->notify.data)
781     XFREE(MTYPE_TMP, peer->notify.data);
782   
783   bgp_sync_delete (peer);
784
785   bgp_unlock(peer->bgp);
786
787   memset (peer, 0, sizeof (struct peer));
788   
789   XFREE (MTYPE_BGP_PEER, peer);
790 }
791                                                 
792 /* increase reference count on a struct peer */
793 struct peer *
794 peer_lock_with_caller (const char *name, struct peer *peer)
795 {
796   assert (peer && (peer->lock >= 0));
797
798 #if 0
799   zlog_debug("%s peer_lock %p %d", name, peer, peer->lock);
800 #endif
801
802   peer->lock++;
803   
804   return peer;
805 }
806
807 /* decrease reference count on a struct peer
808  * struct peer is freed and NULL returned if last reference
809  */
810 struct peer *
811 peer_unlock_with_caller (const char *name, struct peer *peer)
812 {
813   assert (peer && (peer->lock > 0));
814
815 #if 0
816   zlog_debug("%s peer_unlock %p %d", name, peer, peer->lock);
817 #endif
818
819   peer->lock--;
820   
821   if (peer->lock == 0)
822     {
823       peer_free (peer);
824       return NULL;
825     }
826
827   return peer;
828 }
829   
830 /* Allocate new peer object, implicitely locked.  */
831 static struct peer *
832 peer_new (struct bgp *bgp)
833 {
834   afi_t afi;
835   safi_t safi;
836   struct peer *peer;
837   struct servent *sp;
838   
839   /* bgp argument is absolutely required */
840   assert (bgp);
841   if (!bgp)
842     return NULL;
843   
844   /* Allocate new peer. */
845   peer = XCALLOC (MTYPE_BGP_PEER, sizeof (struct peer));
846
847   /* Set default value. */
848   peer->fd = -1;
849   peer->v_start = BGP_INIT_START_TIMER;
850   peer->v_connect = BGP_DEFAULT_CONNECT_RETRY;
851   peer->status = Idle;
852   peer->ostatus = Idle;
853   peer->weight = 0;
854   peer->password = NULL;
855   peer->bgp = bgp;
856   peer = peer_lock (peer); /* initial reference */
857   bgp_lock (bgp);
858
859   /* Set default flags.  */
860   for (afi = AFI_IP; afi < AFI_MAX; afi++)
861     for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
862       {
863         if (! bgp_option_check (BGP_OPT_CONFIG_CISCO))
864           {
865             SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SEND_COMMUNITY);
866             SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SEND_EXT_COMMUNITY);
867             SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SEND_LARGE_COMMUNITY);
868           }
869         peer->orf_plist[afi][safi] = NULL;
870       }
871   SET_FLAG (peer->sflags, PEER_STATUS_CAPABILITY_OPEN);
872
873   /* Create buffers.  */
874   peer->ibuf = stream_new (BGP_MAX_PACKET_SIZE);
875   peer->obuf = stream_fifo_new ();
876
877   /* We use a larger buffer for peer->work in the event that:
878    * - We RX a BGP_UPDATE where the attributes alone are just
879    *   under BGP_MAX_PACKET_SIZE
880    * - The user configures an outbound route-map that does many as-path
881    *   prepends or adds many communities.  At most they can have CMD_ARGC_MAX
882    *   args in a route-map so there is a finite limit on how large they can
883    *   make the attributes.
884    *
885    * Having a buffer with BGP_MAX_PACKET_SIZE_OVERFLOW allows us to avoid bounds
886    * checking for every single attribute as we construct an UPDATE.
887    */
888   peer->work = stream_new (BGP_MAX_PACKET_SIZE + BGP_MAX_PACKET_SIZE_OVERFLOW);
889   peer->scratch = stream_new (BGP_MAX_PACKET_SIZE);
890
891   bgp_sync_init (peer);
892
893   /* Get service port number.  */
894   sp = getservbyname ("bgp", "tcp");
895   peer->port = (sp == NULL) ? BGP_PORT_DEFAULT : ntohs (sp->s_port);
896
897   return peer;
898 }
899
900 /* Create new BGP peer.  */
901 static struct peer *
902 peer_create (union sockunion *su, struct bgp *bgp, as_t local_as,
903              as_t remote_as, afi_t afi, safi_t safi)
904 {
905   int active;
906   struct peer *peer;
907   char buf[SU_ADDRSTRLEN];
908
909   peer = peer_new (bgp);
910   peer->su = *su;
911   peer->local_as = local_as;
912   peer->as = remote_as;
913   peer->local_id = bgp->router_id;
914   peer->v_holdtime = bgp->default_holdtime;
915   peer->v_keepalive = bgp->default_keepalive;
916   if (peer_sort (peer) == BGP_PEER_IBGP)
917     peer->v_routeadv = BGP_DEFAULT_IBGP_ROUTEADV;
918   else
919     peer->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
920     
921   peer = peer_lock (peer); /* bgp peer list reference */
922   listnode_add_sort (bgp->peer, peer);
923
924   active = peer_active (peer);
925
926   if (afi && safi)
927     peer->afc[afi][safi] = 1;
928
929   /* Last read and reset time set */
930   peer->readtime = peer->resettime = bgp_clock ();
931
932   /* Make peer's address string. */
933   sockunion2str (su, buf, SU_ADDRSTRLEN);
934   peer->host = XSTRDUP (MTYPE_BGP_PEER_HOST, buf);
935
936   /* Set up peer's events and timers. */
937   if (! active && peer_active (peer))
938     bgp_timer_set (peer);
939
940   return peer;
941 }
942
943 /* Make accept BGP peer.  Called from bgp_accept (). */
944 struct peer *
945 peer_create_accept (struct bgp *bgp)
946 {
947   struct peer *peer;
948
949   peer = peer_new (bgp);
950   
951   peer = peer_lock (peer); /* bgp peer list reference */
952   listnode_add_sort (bgp->peer, peer);
953
954   return peer;
955 }
956
957 /* Change peer's AS number.  */
958 static void
959 peer_as_change (struct peer *peer, as_t as)
960 {
961   struct peer *conf;
962
963   /* Stop peer. */
964   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
965     {
966       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
967        {
968          peer->last_reset = PEER_DOWN_REMOTE_AS_CHANGE;
969          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
970                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
971        }
972       else
973         BGP_EVENT_ADD (peer, BGP_Stop);
974     }
975   peer->as = as;
976
977   if (bgp_config_check (peer->bgp, BGP_CONFIG_CONFEDERATION)
978       && ! bgp_confederation_peers_check (peer->bgp, as)
979       && peer->bgp->as != as)
980     peer->local_as = peer->bgp->confed_id;
981   else
982     peer->local_as = peer->bgp->as;
983
984   /* Advertisement-interval reset */
985   conf = NULL;
986   if (peer->group)
987     conf = peer->group->conf;
988
989   if (conf && CHECK_FLAG (conf->config, PEER_CONFIG_ROUTEADV))
990       peer->v_routeadv = conf->routeadv;
991   else
992     if (peer_sort (peer) == BGP_PEER_IBGP)
993       peer->v_routeadv = BGP_DEFAULT_IBGP_ROUTEADV;
994     else
995       peer->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
996
997   /* reflector-client reset */
998   if (peer_sort (peer) != BGP_PEER_IBGP)
999     {
1000       UNSET_FLAG (peer->af_flags[AFI_IP][SAFI_UNICAST],
1001                   PEER_FLAG_REFLECTOR_CLIENT);
1002       UNSET_FLAG (peer->af_flags[AFI_IP][SAFI_MULTICAST],
1003                   PEER_FLAG_REFLECTOR_CLIENT);
1004       UNSET_FLAG (peer->af_flags[AFI_IP][SAFI_MPLS_VPN],
1005                   PEER_FLAG_REFLECTOR_CLIENT);
1006       UNSET_FLAG (peer->af_flags[AFI_IP][SAFI_ENCAP],
1007                   PEER_FLAG_REFLECTOR_CLIENT);
1008       UNSET_FLAG (peer->af_flags[AFI_IP6][SAFI_UNICAST],
1009                   PEER_FLAG_REFLECTOR_CLIENT);
1010       UNSET_FLAG (peer->af_flags[AFI_IP6][SAFI_MULTICAST],
1011                   PEER_FLAG_REFLECTOR_CLIENT);
1012       UNSET_FLAG (peer->af_flags[AFI_IP6][SAFI_MPLS_VPN],
1013                   PEER_FLAG_REFLECTOR_CLIENT);
1014       UNSET_FLAG (peer->af_flags[AFI_IP6][SAFI_ENCAP],
1015                   PEER_FLAG_REFLECTOR_CLIENT);
1016     }
1017
1018   /* local-as reset */
1019   if (peer_sort (peer) != BGP_PEER_EBGP)
1020     {
1021       peer->change_local_as = 0;
1022       UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
1023       UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
1024     }
1025 }
1026
1027 /* If peer does not exist, create new one.  If peer already exists,
1028    set AS number to the peer.  */
1029 int
1030 peer_remote_as (struct bgp *bgp, union sockunion *su, as_t *as,
1031                 afi_t afi, safi_t safi)
1032 {
1033   struct peer *peer;
1034   as_t local_as;
1035
1036   peer = peer_lookup (bgp, su);
1037
1038   if (peer)
1039     {
1040       /* When this peer is a member of peer-group.  */
1041       if (peer->group)
1042         {
1043           if (peer->group->conf->as)
1044             {
1045               /* Return peer group's AS number.  */
1046               *as = peer->group->conf->as;
1047               return BGP_ERR_PEER_GROUP_MEMBER;
1048             }
1049           if (peer_sort (peer->group->conf) == BGP_PEER_IBGP)
1050             {
1051               if (bgp->as != *as)
1052                 {
1053                   *as = peer->as;
1054                   return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT;
1055                 }
1056             }
1057           else
1058             {
1059               if (bgp->as == *as)
1060                 {
1061                   *as = peer->as;
1062                   return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT;
1063                 }
1064             }
1065         }
1066
1067       /* Existing peer's AS number change. */
1068       if (peer->as != *as)
1069         peer_as_change (peer, *as);
1070     }
1071   else
1072     {
1073
1074       /* If the peer is not part of our confederation, and its not an
1075          iBGP peer then spoof the source AS */
1076       if (bgp_config_check (bgp, BGP_CONFIG_CONFEDERATION)
1077           && ! bgp_confederation_peers_check (bgp, *as) 
1078           && bgp->as != *as)
1079         local_as = bgp->confed_id;
1080       else
1081         local_as = bgp->as;
1082       
1083       /* If this is IPv4 unicast configuration and "no bgp default
1084          ipv4-unicast" is specified. */
1085
1086       if (bgp_flag_check (bgp, BGP_FLAG_NO_DEFAULT_IPV4)
1087           && afi == AFI_IP && safi == SAFI_UNICAST)
1088         peer_create (su, bgp, local_as, *as, 0, 0); 
1089       else
1090         peer_create (su, bgp, local_as, *as, afi, safi); 
1091     }
1092
1093   return 0;
1094 }
1095
1096 /* Activate the peer or peer group for specified AFI and SAFI.  */
1097 int
1098 peer_activate (struct peer *peer, afi_t afi, safi_t safi)
1099 {
1100   int active;
1101
1102   if (peer->afc[afi][safi])
1103     return 0;
1104
1105   /* Activate the address family configuration. */
1106   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
1107     peer->afc[afi][safi] = 1;
1108   else
1109     {
1110       active = peer_active (peer);
1111
1112       peer->afc[afi][safi] = 1;
1113
1114       if (! active && peer_active (peer))
1115         bgp_timer_set (peer);
1116       else
1117         {
1118           if (peer->status == Established)
1119             {
1120               if (CHECK_FLAG (peer->cap, PEER_CAP_DYNAMIC_RCV))
1121                 {
1122                   peer->afc_adv[afi][safi] = 1;
1123                   bgp_capability_send (peer, afi, safi,
1124                                        CAPABILITY_CODE_MP,
1125                                        CAPABILITY_ACTION_SET);
1126                   if (peer->afc_recv[afi][safi])
1127                     {
1128                       peer->afc_nego[afi][safi] = 1;
1129                       bgp_announce_route (peer, afi, safi);
1130                     }
1131                 }
1132               else
1133                {
1134                  peer->last_reset = PEER_DOWN_AF_ACTIVATE;
1135                  bgp_notify_send (peer, BGP_NOTIFY_CEASE,
1136                                   BGP_NOTIFY_CEASE_CONFIG_CHANGE);
1137                }
1138             }
1139         }
1140     }
1141   return 0;
1142 }
1143
1144 int
1145 peer_deactivate (struct peer *peer, afi_t afi, safi_t safi)
1146 {
1147   struct peer_group *group;
1148   struct peer *peer1;
1149   struct listnode *node, *nnode;
1150
1151   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
1152     {
1153       group = peer->group;
1154
1155       for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer1))
1156         {
1157           if (peer1->af_group[afi][safi])
1158             return BGP_ERR_PEER_GROUP_MEMBER_EXISTS;
1159         }
1160     }
1161   else
1162     {
1163       if (peer->af_group[afi][safi])
1164         return BGP_ERR_PEER_BELONGS_TO_GROUP;
1165     }
1166
1167   if (! peer->afc[afi][safi])
1168     return 0;
1169
1170   /* De-activate the address family configuration. */
1171   peer->afc[afi][safi] = 0;
1172   peer_af_flag_reset (peer, afi, safi);
1173
1174   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
1175     {  
1176       if (peer->status == Established)
1177         {
1178           if (CHECK_FLAG (peer->cap, PEER_CAP_DYNAMIC_RCV))
1179             {
1180               peer->afc_adv[afi][safi] = 0;
1181               peer->afc_nego[afi][safi] = 0;
1182
1183               if (peer_active_nego (peer))
1184                 {
1185                   bgp_capability_send (peer, afi, safi,
1186                                        CAPABILITY_CODE_MP,
1187                                        CAPABILITY_ACTION_UNSET);
1188                   bgp_clear_route (peer, afi, safi, BGP_CLEAR_ROUTE_NORMAL);
1189                   peer->pcount[afi][safi] = 0;
1190                 }
1191               else
1192                {
1193                  peer->last_reset = PEER_DOWN_NEIGHBOR_DELETE;
1194                  bgp_notify_send (peer, BGP_NOTIFY_CEASE,
1195                                   BGP_NOTIFY_CEASE_CONFIG_CHANGE);
1196                }
1197             }
1198           else
1199            {
1200              peer->last_reset = PEER_DOWN_NEIGHBOR_DELETE;
1201              bgp_notify_send (peer, BGP_NOTIFY_CEASE,
1202                               BGP_NOTIFY_CEASE_CONFIG_CHANGE);
1203            }
1204         }
1205     }
1206   return 0;
1207 }
1208
1209 int
1210 peer_afc_set (struct peer *peer, afi_t afi, safi_t safi, int enable)
1211 {
1212   if (enable)
1213     return peer_activate (peer, afi, safi);
1214   else
1215     return peer_deactivate (peer, afi, safi);
1216 }
1217
1218 static void
1219 peer_nsf_stop (struct peer *peer)
1220 {
1221   afi_t afi;
1222   safi_t safi;
1223
1224   UNSET_FLAG (peer->sflags, PEER_STATUS_NSF_WAIT);
1225   UNSET_FLAG (peer->sflags, PEER_STATUS_NSF_MODE);
1226
1227   for (afi = AFI_IP ; afi < AFI_MAX ; afi++)
1228     for (safi = SAFI_UNICAST ; safi < SAFI_RESERVED_3 ; safi++)
1229       peer->nsf[afi][safi] = 0;
1230
1231   if (peer->t_gr_restart)
1232     {
1233       BGP_TIMER_OFF (peer->t_gr_restart);
1234       if (BGP_DEBUG (events, EVENTS))
1235         zlog_debug ("%s graceful restart timer stopped", peer->host);
1236     }
1237   if (peer->t_gr_stale)
1238     {
1239       BGP_TIMER_OFF (peer->t_gr_stale);
1240       if (BGP_DEBUG (events, EVENTS))
1241         zlog_debug ("%s graceful restart stalepath timer stopped", peer->host);
1242     }
1243   bgp_clear_route_all (peer);
1244 }
1245
1246 /* Delete peer from confguration.
1247  *
1248  * The peer is moved to a dead-end "Deleted" neighbour-state, to allow
1249  * it to "cool off" and refcounts to hit 0, at which state it is freed.
1250  *
1251  * This function /should/ take care to be idempotent, to guard against
1252  * it being called multiple times through stray events that come in
1253  * that happen to result in this function being called again.  That
1254  * said, getting here for a "Deleted" peer is a bug in the neighbour
1255  * FSM.
1256  */
1257 int
1258 peer_delete (struct peer *peer)
1259 {
1260   int i;
1261   afi_t afi;
1262   safi_t safi;
1263   struct bgp *bgp;
1264   struct bgp_filter *filter;
1265   struct listnode *pn;
1266
1267   assert (peer->status != Deleted);
1268   
1269   bgp = peer->bgp;
1270
1271   if (CHECK_FLAG (peer->sflags, PEER_STATUS_NSF_WAIT))
1272     peer_nsf_stop (peer);
1273
1274   /* If this peer belongs to peer group, clear up the
1275      relationship.  */
1276   if (peer->group)
1277     {
1278       if ((pn = listnode_lookup (peer->group->peer, peer)))
1279         {
1280           peer = peer_unlock (peer); /* group->peer list reference */
1281           list_delete_node (peer->group->peer, pn);
1282         }
1283       peer->group = NULL;
1284     }
1285   
1286   /* Withdraw all information from routing table.  We can not use
1287    * BGP_EVENT_ADD (peer, BGP_Stop) at here.  Because the event is
1288    * executed after peer structure is deleted.
1289    */
1290   peer->last_reset = PEER_DOWN_NEIGHBOR_DELETE;
1291   bgp_stop (peer);
1292   bgp_fsm_change_status (peer, Deleted);
1293   
1294   /* Remove from NHT */
1295   bgp_unlink_nexthop_by_peer (peer);
1296   
1297   /* Password configuration */
1298   if (peer->password)
1299     {
1300       XFREE (MTYPE_PEER_PASSWORD, peer->password);
1301       peer->password = NULL;
1302
1303       if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
1304         bgp_md5_set (peer);
1305     }
1306   
1307   bgp_timer_set (peer); /* stops all timers for Deleted */
1308   
1309   /* Delete from all peer list. */
1310   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP)
1311       && (pn = listnode_lookup (bgp->peer, peer)))
1312     {
1313       peer_unlock (peer); /* bgp peer list reference */
1314       list_delete_node (bgp->peer, pn);
1315     }
1316       
1317   if (peer_rsclient_active (peer)
1318       && (pn = listnode_lookup (bgp->rsclient, peer)))
1319     {
1320       peer_unlock (peer); /* rsclient list reference */
1321       list_delete_node (bgp->rsclient, pn);
1322
1323       /* Clear our own rsclient ribs. */
1324       for (afi = AFI_IP; afi < AFI_MAX; afi++)
1325         for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
1326           if (CHECK_FLAG(peer->af_flags[afi][safi],
1327                          PEER_FLAG_RSERVER_CLIENT))
1328             bgp_clear_route (peer, afi, safi, BGP_CLEAR_ROUTE_MY_RSCLIENT);
1329     }
1330
1331   /* Free RIB for any family in which peer is RSERVER_CLIENT, and is not
1332       member of a peer_group. */
1333   for (afi = AFI_IP; afi < AFI_MAX; afi++)
1334     for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
1335       if (peer->rib[afi][safi] && ! peer->af_group[afi][safi])
1336         bgp_table_finish (&peer->rib[afi][safi]);
1337
1338   /* Buffers.  */
1339   if (peer->ibuf)
1340     {
1341       stream_free (peer->ibuf);
1342       peer->ibuf = NULL;
1343     }
1344
1345   if (peer->obuf)
1346     {
1347       stream_fifo_free (peer->obuf);
1348       peer->obuf = NULL;
1349     }
1350
1351   if (peer->work)
1352     {
1353       stream_free (peer->work);
1354       peer->work = NULL;
1355     }
1356
1357   if (peer->scratch)
1358     {
1359       stream_free(peer->scratch);
1360       peer->scratch = NULL;
1361     }
1362
1363   /* Local and remote addresses. */
1364   if (peer->su_local)
1365     {
1366       sockunion_free (peer->su_local);
1367       peer->su_local = NULL;
1368     }
1369
1370   if (peer->su_remote)
1371     {
1372       sockunion_free (peer->su_remote);
1373       peer->su_remote = NULL;
1374     }
1375   
1376   /* Free filter related memory.  */
1377   for (afi = AFI_IP; afi < AFI_MAX; afi++)
1378     for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
1379       {
1380         filter = &peer->filter[afi][safi];
1381
1382         for (i = FILTER_IN; i < FILTER_MAX; i++)
1383           {
1384             if (filter->dlist[i].name)
1385               {
1386                 free(filter->dlist[i].name);
1387                 filter->dlist[i].name = NULL;
1388               }
1389
1390             if (filter->plist[i].name)
1391               {
1392                 free(filter->plist[i].name);
1393                 filter->plist[i].name = NULL;
1394               }
1395
1396             if (filter->aslist[i].name)
1397               {
1398                 free(filter->aslist[i].name);
1399                 filter->aslist[i].name = NULL;
1400               }
1401           }
1402
1403         for (i = RMAP_IN; i < RMAP_MAX; i++)
1404           {
1405             if (filter->map[i].name)
1406               {
1407                 free (filter->map[i].name);
1408                 filter->map[i].name = NULL;
1409               }
1410           }
1411
1412         if (filter->usmap.name)
1413           {
1414             free (filter->usmap.name);
1415             filter->usmap.name = NULL;
1416           }
1417
1418         if (peer->default_rmap[afi][safi].name)
1419           {
1420             free (peer->default_rmap[afi][safi].name);
1421             peer->default_rmap[afi][safi].name = NULL;
1422           }
1423       }
1424   
1425   if (CHECK_FLAG(bgp->flags, BGP_FLAG_DELETING))
1426     bgp_peer_clear_node_queue_drain_immediate(peer);
1427
1428   peer_unlock (peer); /* initial reference */
1429
1430   return 0;
1431 }
1432
1433 static int
1434 peer_group_cmp (struct peer_group *g1, struct peer_group *g2)
1435 {
1436   return strcmp (g1->name, g2->name);
1437 }
1438
1439 /* If peer is configured at least one address family return 1. */
1440 static int
1441 peer_group_active (struct peer *peer)
1442 {
1443   if (peer->af_group[AFI_IP][SAFI_UNICAST]
1444       || peer->af_group[AFI_IP][SAFI_MULTICAST]
1445       || peer->af_group[AFI_IP][SAFI_MPLS_VPN]
1446       || peer->af_group[AFI_IP][SAFI_ENCAP]
1447       || peer->af_group[AFI_IP6][SAFI_UNICAST]
1448       || peer->af_group[AFI_IP6][SAFI_MULTICAST]
1449       || peer->af_group[AFI_IP6][SAFI_MPLS_VPN]
1450       || peer->af_group[AFI_IP6][SAFI_ENCAP])
1451     return 1;
1452   return 0;
1453 }
1454
1455 /* Peer group cofiguration. */
1456 static struct peer_group *
1457 peer_group_new (void)
1458 {
1459   return (struct peer_group *) XCALLOC (MTYPE_PEER_GROUP,
1460                                         sizeof (struct peer_group));
1461 }
1462
1463 static void
1464 peer_group_free (struct peer_group *group)
1465 {
1466   XFREE (MTYPE_PEER_GROUP, group);
1467 }
1468
1469 struct peer_group *
1470 peer_group_lookup (struct bgp *bgp, const char *name)
1471 {
1472   struct peer_group *group;
1473   struct listnode *node, *nnode;
1474
1475   for (ALL_LIST_ELEMENTS (bgp->group, node, nnode, group))
1476     {
1477       if (strcmp (group->name, name) == 0)
1478         return group;
1479     }
1480   return NULL;
1481 }
1482
1483 struct peer_group *
1484 peer_group_get (struct bgp *bgp, const char *name)
1485 {
1486   struct peer_group *group;
1487
1488   group = peer_group_lookup (bgp, name);
1489   if (group)
1490     return group;
1491
1492   group = peer_group_new ();
1493   group->bgp = bgp;
1494   group->name = strdup (name);
1495   group->peer = list_new ();
1496   group->conf = peer_new (bgp);
1497   if (! bgp_flag_check (bgp, BGP_FLAG_NO_DEFAULT_IPV4))
1498     group->conf->afc[AFI_IP][SAFI_UNICAST] = 1;
1499   group->conf->host = XSTRDUP (MTYPE_BGP_PEER_HOST, name);
1500   group->conf->group = group;
1501   group->conf->as = 0; 
1502   group->conf->ttl = 0;
1503   group->conf->gtsm_hops = 0;
1504   group->conf->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
1505   UNSET_FLAG (group->conf->config, PEER_CONFIG_TIMER);
1506   UNSET_FLAG (group->conf->config, PEER_CONFIG_CONNECT);
1507   group->conf->keepalive = 0;
1508   group->conf->holdtime = 0;
1509   group->conf->connect = 0;
1510   SET_FLAG (group->conf->sflags, PEER_STATUS_GROUP);
1511   listnode_add_sort (bgp->group, group);
1512
1513   return 0;
1514 }
1515
1516 static void 
1517 peer_group2peer_config_copy (struct peer_group *group, struct peer *peer,
1518                              afi_t afi, safi_t safi)
1519 {
1520   int in = FILTER_IN;
1521   int out = FILTER_OUT;
1522   struct peer *conf;
1523   struct bgp_filter *pfilter;
1524   struct bgp_filter *gfilter;
1525
1526   conf = group->conf;
1527   pfilter = &peer->filter[afi][safi];
1528   gfilter = &conf->filter[afi][safi];
1529
1530   /* remote-as */
1531   if (conf->as)
1532     peer->as = conf->as;
1533
1534   /* remote-as */
1535   if (conf->change_local_as)
1536     peer->change_local_as = conf->change_local_as;
1537
1538   /* TTL */
1539   peer->ttl = conf->ttl;
1540
1541   /* GTSM hops */
1542   peer->gtsm_hops = conf->gtsm_hops;
1543
1544   /* Weight */
1545   peer->weight = conf->weight;
1546
1547   /* peer flags apply */
1548   peer->flags = conf->flags;
1549   /* peer af_flags apply */
1550   peer->af_flags[afi][safi] = conf->af_flags[afi][safi];
1551   /* peer config apply */
1552   peer->config = conf->config;
1553
1554   /* peer timers apply */
1555   peer->holdtime = conf->holdtime;
1556   peer->keepalive = conf->keepalive;
1557   peer->connect = conf->connect;
1558   if (CHECK_FLAG (conf->config, PEER_CONFIG_CONNECT))
1559     peer->v_connect = conf->connect;
1560   else
1561     peer->v_connect = BGP_DEFAULT_CONNECT_RETRY;
1562
1563   /* advertisement-interval reset */
1564   if (CHECK_FLAG (conf->config, PEER_CONFIG_ROUTEADV))
1565       peer->v_routeadv = conf->routeadv;
1566   else
1567       if (peer_sort (peer) == BGP_PEER_IBGP)
1568         peer->v_routeadv = BGP_DEFAULT_IBGP_ROUTEADV;
1569       else
1570         peer->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
1571
1572   /* password apply */
1573   if (conf->password && !peer->password)
1574     peer->password =  XSTRDUP (MTYPE_PEER_PASSWORD, conf->password);
1575
1576   bgp_md5_set (peer);
1577
1578   /* maximum-prefix */
1579   peer->pmax[afi][safi] = conf->pmax[afi][safi];
1580   peer->pmax_threshold[afi][safi] = conf->pmax_threshold[afi][safi];
1581   peer->pmax_restart[afi][safi] = conf->pmax_restart[afi][safi];
1582
1583   /* allowas-in */
1584   peer->allowas_in[afi][safi] = conf->allowas_in[afi][safi];
1585
1586   /* route-server-client */
1587   if (CHECK_FLAG(conf->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT))
1588     {
1589       /* Make peer's RIB point to group's RIB. */
1590       peer->rib[afi][safi] = group->conf->rib[afi][safi];
1591
1592       /* Import policy. */
1593       if (pfilter->map[RMAP_IMPORT].name)
1594         free (pfilter->map[RMAP_IMPORT].name);
1595       if (gfilter->map[RMAP_IMPORT].name)
1596         {
1597           pfilter->map[RMAP_IMPORT].name = strdup (gfilter->map[RMAP_IMPORT].name);
1598           pfilter->map[RMAP_IMPORT].map = gfilter->map[RMAP_IMPORT].map;
1599         }
1600       else
1601         {
1602           pfilter->map[RMAP_IMPORT].name = NULL;
1603           pfilter->map[RMAP_IMPORT].map = NULL;
1604         }
1605
1606       /* Export policy. */
1607       if (gfilter->map[RMAP_EXPORT].name && ! pfilter->map[RMAP_EXPORT].name)
1608         {
1609           pfilter->map[RMAP_EXPORT].name = strdup (gfilter->map[RMAP_EXPORT].name);
1610           pfilter->map[RMAP_EXPORT].map = gfilter->map[RMAP_EXPORT].map;
1611         }
1612     }
1613
1614   /* default-originate route-map */
1615   if (conf->default_rmap[afi][safi].name)
1616     {
1617       if (peer->default_rmap[afi][safi].name)
1618         free (peer->default_rmap[afi][safi].name);
1619       peer->default_rmap[afi][safi].name = strdup (conf->default_rmap[afi][safi].name);
1620       peer->default_rmap[afi][safi].map = conf->default_rmap[afi][safi].map;
1621     }
1622
1623   /* update-source apply */
1624   if (conf->update_source)
1625     {
1626       if (peer->update_source)
1627         sockunion_free (peer->update_source);
1628       if (peer->update_if)
1629         {
1630           XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
1631           peer->update_if = NULL;
1632         }
1633       peer->update_source = sockunion_dup (conf->update_source);
1634     }
1635   else if (conf->update_if)
1636     {
1637       if (peer->update_if)
1638         XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
1639       if (peer->update_source)
1640         {
1641           sockunion_free (peer->update_source);
1642           peer->update_source = NULL;
1643         }
1644       peer->update_if = XSTRDUP (MTYPE_PEER_UPDATE_SOURCE, conf->update_if);
1645     }
1646
1647   /* inbound filter apply */
1648   if (gfilter->dlist[in].name && ! pfilter->dlist[in].name)
1649     {
1650       if (pfilter->dlist[in].name)
1651         free (pfilter->dlist[in].name);
1652       pfilter->dlist[in].name = strdup (gfilter->dlist[in].name);
1653       pfilter->dlist[in].alist = gfilter->dlist[in].alist;
1654     }
1655   if (gfilter->plist[in].name && ! pfilter->plist[in].name)
1656     {
1657       if (pfilter->plist[in].name)
1658         free (pfilter->plist[in].name);
1659       pfilter->plist[in].name = strdup (gfilter->plist[in].name);
1660       pfilter->plist[in].plist = gfilter->plist[in].plist;
1661     }
1662   if (gfilter->aslist[in].name && ! pfilter->aslist[in].name)
1663     {
1664       if (pfilter->aslist[in].name)
1665         free (pfilter->aslist[in].name);
1666       pfilter->aslist[in].name = strdup (gfilter->aslist[in].name);
1667       pfilter->aslist[in].aslist = gfilter->aslist[in].aslist;
1668     }
1669   if (gfilter->map[RMAP_IN].name && ! pfilter->map[RMAP_IN].name)
1670     {
1671       if (pfilter->map[RMAP_IN].name)
1672         free (pfilter->map[RMAP_IN].name);
1673       pfilter->map[RMAP_IN].name = strdup (gfilter->map[RMAP_IN].name);
1674       pfilter->map[RMAP_IN].map = gfilter->map[RMAP_IN].map;
1675     }
1676
1677   /* outbound filter apply */
1678   if (gfilter->dlist[out].name)
1679     {
1680       if (pfilter->dlist[out].name)
1681         free (pfilter->dlist[out].name);
1682       pfilter->dlist[out].name = strdup (gfilter->dlist[out].name);
1683       pfilter->dlist[out].alist = gfilter->dlist[out].alist;
1684     }
1685   else
1686     {
1687       if (pfilter->dlist[out].name)
1688         free (pfilter->dlist[out].name);
1689       pfilter->dlist[out].name = NULL;
1690       pfilter->dlist[out].alist = NULL;
1691     }
1692   if (gfilter->plist[out].name)
1693     {
1694       if (pfilter->plist[out].name)
1695         free (pfilter->plist[out].name);
1696       pfilter->plist[out].name = strdup (gfilter->plist[out].name);
1697       pfilter->plist[out].plist = gfilter->plist[out].plist;
1698     }
1699   else
1700     {
1701       if (pfilter->plist[out].name)
1702         free (pfilter->plist[out].name);
1703       pfilter->plist[out].name = NULL;
1704       pfilter->plist[out].plist = NULL;
1705     }
1706   if (gfilter->aslist[out].name)
1707     {
1708       if (pfilter->aslist[out].name)
1709         free (pfilter->aslist[out].name);
1710       pfilter->aslist[out].name = strdup (gfilter->aslist[out].name);
1711       pfilter->aslist[out].aslist = gfilter->aslist[out].aslist;
1712     }
1713   else
1714     {
1715       if (pfilter->aslist[out].name)
1716         free (pfilter->aslist[out].name);
1717       pfilter->aslist[out].name = NULL;
1718       pfilter->aslist[out].aslist = NULL;
1719     }
1720   if (gfilter->map[RMAP_OUT].name)
1721     {
1722       if (pfilter->map[RMAP_OUT].name)
1723         free (pfilter->map[RMAP_OUT].name);
1724       pfilter->map[RMAP_OUT].name = strdup (gfilter->map[RMAP_OUT].name);
1725       pfilter->map[RMAP_OUT].map = gfilter->map[RMAP_OUT].map;
1726     }
1727   else
1728     {
1729       if (pfilter->map[RMAP_OUT].name)
1730         free (pfilter->map[RMAP_OUT].name);
1731       pfilter->map[RMAP_OUT].name = NULL;
1732       pfilter->map[RMAP_OUT].map = NULL;
1733     }
1734
1735  /* RS-client's import/export route-maps. */
1736   if (gfilter->map[RMAP_IMPORT].name)
1737     {
1738       if (pfilter->map[RMAP_IMPORT].name)
1739         free (pfilter->map[RMAP_IMPORT].name);
1740       pfilter->map[RMAP_IMPORT].name = strdup (gfilter->map[RMAP_IMPORT].name);
1741       pfilter->map[RMAP_IMPORT].map = gfilter->map[RMAP_IMPORT].map;
1742     }
1743   else
1744     {
1745       if (pfilter->map[RMAP_IMPORT].name)
1746         free (pfilter->map[RMAP_IMPORT].name);
1747       pfilter->map[RMAP_IMPORT].name = NULL;
1748       pfilter->map[RMAP_IMPORT].map = NULL;
1749     }
1750   if (gfilter->map[RMAP_EXPORT].name && ! pfilter->map[RMAP_EXPORT].name)
1751     {
1752       if (pfilter->map[RMAP_EXPORT].name)
1753         free (pfilter->map[RMAP_EXPORT].name);
1754       pfilter->map[RMAP_EXPORT].name = strdup (gfilter->map[RMAP_EXPORT].name);
1755       pfilter->map[RMAP_EXPORT].map = gfilter->map[RMAP_EXPORT].map;
1756     }
1757
1758   if (gfilter->usmap.name)
1759     {
1760       if (pfilter->usmap.name)
1761         free (pfilter->usmap.name);
1762       pfilter->usmap.name = strdup (gfilter->usmap.name);
1763       pfilter->usmap.map = gfilter->usmap.map;
1764     }
1765   else
1766     {
1767       if (pfilter->usmap.name)
1768         free (pfilter->usmap.name);
1769       pfilter->usmap.name = NULL;
1770       pfilter->usmap.map = NULL;
1771     }
1772
1773
1774 /* Peer group's remote AS configuration.  */
1775 int
1776 peer_group_remote_as (struct bgp *bgp, const char *group_name, as_t *as)
1777 {
1778   struct peer_group *group;
1779   struct peer *peer;
1780   struct listnode *node, *nnode;
1781
1782   group = peer_group_lookup (bgp, group_name);
1783   if (! group)
1784     return -1;
1785
1786   if (group->conf->as == *as)
1787     return 0;
1788
1789   /* When we setup peer-group AS number all peer group member's AS
1790      number must be updated to same number.  */
1791   peer_as_change (group->conf, *as);
1792
1793   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
1794     {
1795       if (peer->as != *as)
1796         peer_as_change (peer, *as);
1797     }
1798
1799   return 0;
1800 }
1801
1802 int
1803 peer_ttl (struct peer *peer)
1804 {
1805   if (peer->ttl)
1806     return peer->ttl;
1807   if (peer->gtsm_hops || peer->sort == BGP_PEER_IBGP)
1808     return 255;
1809   return 1;
1810 }
1811
1812 int
1813 peer_group_delete (struct peer_group *group)
1814 {
1815   struct bgp *bgp;
1816   struct peer *peer;
1817   struct listnode *node, *nnode;
1818
1819   bgp = group->bgp;
1820
1821   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
1822     {
1823       peer_delete (peer);
1824     }
1825   list_delete (group->peer);
1826
1827   free (group->name);
1828   group->name = NULL;
1829
1830   group->conf->group = NULL;
1831   peer_delete (group->conf);
1832
1833   /* Delete from all peer_group list. */
1834   listnode_delete (bgp->group, group);
1835
1836   peer_group_free (group);
1837
1838   return 0;
1839 }
1840
1841 int
1842 peer_group_remote_as_delete (struct peer_group *group)
1843 {
1844   struct peer *peer;
1845   struct listnode *node, *nnode;
1846
1847   if (! group->conf->as)
1848     return 0;
1849
1850   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
1851     {
1852       peer_delete (peer);
1853     }
1854   list_delete_all_node (group->peer);
1855
1856   group->conf->as = 0;
1857
1858   return 0;
1859 }
1860
1861 /* Bind specified peer to peer group.  */
1862 int
1863 peer_group_bind (struct bgp *bgp, union sockunion *su,
1864                  struct peer_group *group, afi_t afi, safi_t safi, as_t *as)
1865 {
1866   struct peer *peer;
1867   int first_member = 0;
1868
1869   /* Check peer group's address family.  */
1870   if (! group->conf->afc[afi][safi])
1871     return BGP_ERR_PEER_GROUP_AF_UNCONFIGURED;
1872
1873   /* Lookup the peer.  */
1874   peer = peer_lookup (bgp, su);
1875
1876   /* Create a new peer. */
1877   if (! peer)
1878     {
1879       if (! group->conf->as)
1880         return BGP_ERR_PEER_GROUP_NO_REMOTE_AS;
1881
1882       peer = peer_create (su, bgp, bgp->as, group->conf->as, afi, safi);
1883       peer->group = group;
1884       peer->af_group[afi][safi] = 1;
1885
1886       peer = peer_lock (peer); /* group->peer list reference */
1887       listnode_add (group->peer, peer);
1888       peer_group2peer_config_copy (group, peer, afi, safi);
1889
1890       return 0;
1891     }
1892
1893   /* When the peer already belongs to peer group, check the consistency.  */
1894   if (peer->af_group[afi][safi])
1895     {
1896       if (strcmp (peer->group->name, group->name) != 0)
1897         return BGP_ERR_PEER_GROUP_CANT_CHANGE;
1898
1899       return 0;
1900     }
1901
1902   /* Check current peer group configuration.  */
1903   if (peer_group_active (peer)
1904       && strcmp (peer->group->name, group->name) != 0)
1905     return BGP_ERR_PEER_GROUP_MISMATCH;
1906
1907   if (! group->conf->as)
1908     {
1909       if (peer_sort (group->conf) != BGP_PEER_INTERNAL
1910           && peer_sort (group->conf) != peer_sort (peer))
1911         {
1912           if (as)
1913             *as = peer->as;
1914           return BGP_ERR_PEER_GROUP_PEER_TYPE_DIFFERENT;
1915         }
1916
1917       if (peer_sort (group->conf) == BGP_PEER_INTERNAL)
1918         first_member = 1;
1919     }
1920
1921   peer->af_group[afi][safi] = 1;
1922   peer->afc[afi][safi] = 1;
1923   if (! peer->group)
1924     {
1925       peer->group = group;
1926       
1927       peer = peer_lock (peer); /* group->peer list reference */
1928       listnode_add (group->peer, peer);
1929     }
1930   else
1931     assert (group && peer->group == group);
1932
1933   if (first_member)
1934     {
1935       /* Advertisement-interval reset */
1936       if (! CHECK_FLAG (group->conf->config, PEER_CONFIG_ROUTEADV))
1937         {
1938           if (peer_sort (group->conf) == BGP_PEER_IBGP)
1939             group->conf->v_routeadv = BGP_DEFAULT_IBGP_ROUTEADV;
1940           else
1941             group->conf->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
1942         }
1943
1944       /* local-as reset */
1945       if (peer_sort (group->conf) != BGP_PEER_EBGP)
1946         {
1947           group->conf->change_local_as = 0;
1948           UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
1949           UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
1950         }
1951     }
1952
1953   if (CHECK_FLAG(peer->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT))
1954     {
1955       struct listnode *pn;
1956       
1957       /* If it's not configured as RSERVER_CLIENT in any other address
1958           family, without being member of a peer_group, remove it from
1959           list bgp->rsclient.*/
1960       if (! peer_rsclient_active (peer)
1961           && (pn = listnode_lookup (bgp->rsclient, peer)))
1962         {
1963           peer_unlock (peer); /* peer rsclient reference */
1964           list_delete_node (bgp->rsclient, pn);
1965
1966           /* Clear our own rsclient rib for this afi/safi. */
1967           bgp_clear_route (peer, afi, safi, BGP_CLEAR_ROUTE_MY_RSCLIENT);
1968         }
1969
1970       bgp_table_finish (&peer->rib[afi][safi]);
1971
1972       /* Import policy. */
1973       if (peer->filter[afi][safi].map[RMAP_IMPORT].name)
1974         {
1975           free (peer->filter[afi][safi].map[RMAP_IMPORT].name);
1976           peer->filter[afi][safi].map[RMAP_IMPORT].name = NULL;
1977           peer->filter[afi][safi].map[RMAP_IMPORT].map = NULL;
1978         }
1979
1980       /* Export policy. */
1981       if (! CHECK_FLAG(group->conf->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT)
1982               && peer->filter[afi][safi].map[RMAP_EXPORT].name)
1983         {
1984           free (peer->filter[afi][safi].map[RMAP_EXPORT].name);
1985           peer->filter[afi][safi].map[RMAP_EXPORT].name = NULL;
1986           peer->filter[afi][safi].map[RMAP_EXPORT].map = NULL;
1987         }
1988     }
1989
1990   peer_group2peer_config_copy (group, peer, afi, safi);
1991
1992   if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
1993     {
1994       peer->last_reset = PEER_DOWN_RMAP_BIND;
1995       bgp_notify_send (peer, BGP_NOTIFY_CEASE,
1996                       BGP_NOTIFY_CEASE_CONFIG_CHANGE);
1997     }
1998   else
1999     BGP_EVENT_ADD (peer, BGP_Stop);
2000
2001   return 0;
2002 }
2003
2004 int
2005 peer_group_unbind (struct bgp *bgp, struct peer *peer,
2006                    struct peer_group *group, afi_t afi, safi_t safi)
2007 {
2008   if (! peer->af_group[afi][safi])
2009       return 0;
2010
2011   if (group != peer->group)
2012     return BGP_ERR_PEER_GROUP_MISMATCH;
2013
2014   peer->af_group[afi][safi] = 0;
2015   peer->afc[afi][safi] = 0;
2016   peer_af_flag_reset (peer, afi, safi);
2017
2018   if (peer->rib[afi][safi])
2019     peer->rib[afi][safi] = NULL;
2020
2021   if (! peer_group_active (peer))
2022     {
2023       assert (listnode_lookup (group->peer, peer));
2024       peer_unlock (peer); /* peer group list reference */
2025       listnode_delete (group->peer, peer);
2026       peer->group = NULL;
2027       if (group->conf->as)
2028         {
2029           peer_delete (peer);
2030           return 0;
2031         }
2032       peer_global_config_reset (peer);
2033     }
2034
2035   if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2036     {
2037       peer->last_reset = PEER_DOWN_RMAP_UNBIND;
2038       bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2039                       BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2040     }
2041   else
2042     BGP_EVENT_ADD (peer, BGP_Stop);
2043
2044   return 0;
2045 }
2046
2047
2048 static int
2049 bgp_startup_timer_expire (struct thread *thread)
2050 {
2051   struct bgp *bgp;
2052
2053   bgp = THREAD_ARG (thread);
2054   bgp->t_startup = NULL;
2055
2056   return 0;
2057 }
2058
2059 /* BGP instance creation by `router bgp' commands. */
2060 static struct bgp *
2061 bgp_create (as_t *as, const char *name)
2062 {
2063   struct bgp *bgp;
2064   afi_t afi;
2065   safi_t safi;
2066
2067   if ( (bgp = XCALLOC (MTYPE_BGP, sizeof (struct bgp))) == NULL)
2068     return NULL;
2069   
2070   bgp_lock (bgp);
2071   bgp->peer_self = peer_new (bgp);
2072   bgp->peer_self->host = XSTRDUP (MTYPE_BGP_PEER_HOST, "Static announcement");
2073
2074   bgp->peer = list_new ();
2075   bgp->peer->cmp = (int (*)(void *, void *)) peer_cmp;
2076
2077   bgp->group = list_new ();
2078   bgp->group->cmp = (int (*)(void *, void *)) peer_group_cmp;
2079
2080   bgp->rsclient = list_new ();
2081   bgp->rsclient->cmp = (int (*)(void*, void*)) peer_cmp;
2082
2083   for (afi = AFI_IP; afi < AFI_MAX; afi++)
2084     for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
2085       {
2086         bgp->route[afi][safi] = bgp_table_init (afi, safi);
2087         bgp->aggregate[afi][safi] = bgp_table_init (afi, safi);
2088         bgp->rib[afi][safi] = bgp_table_init (afi, safi);
2089         bgp->maxpaths[afi][safi].maxpaths_ebgp = BGP_DEFAULT_MAXPATHS;
2090         bgp->maxpaths[afi][safi].maxpaths_ibgp = BGP_DEFAULT_MAXPATHS;
2091       }
2092
2093   bgp->default_local_pref = BGP_DEFAULT_LOCAL_PREF;
2094   bgp->default_holdtime = BGP_DEFAULT_HOLDTIME;
2095   bgp->default_keepalive = BGP_DEFAULT_KEEPALIVE;
2096   bgp->restart_time = BGP_DEFAULT_RESTART_TIME;
2097   bgp->stalepath_time = BGP_DEFAULT_STALEPATH_TIME;
2098   bgp_flag_set (bgp, BGP_FLAG_LOG_NEIGHBOR_CHANGES);
2099
2100   bgp->as = *as;
2101
2102   if (name)
2103     bgp->name = strdup (name);
2104
2105   THREAD_TIMER_ON (bm->master, bgp->t_startup, bgp_startup_timer_expire,
2106                    bgp, bgp->restart_time);
2107
2108   return bgp;
2109 }
2110
2111 /* Return first entry of BGP. */
2112 struct bgp *
2113 bgp_get_default (void)
2114 {
2115   if (bm && bm->bgp && bm->bgp->head)
2116     return (listgetdata (listhead (bm->bgp)));
2117   return NULL;
2118 }
2119
2120 /* Lookup BGP entry. */
2121 struct bgp *
2122 bgp_lookup (as_t as, const char *name)
2123 {
2124   struct bgp *bgp;
2125   struct listnode *node, *nnode;
2126
2127   for (ALL_LIST_ELEMENTS (bm->bgp, node, nnode, bgp))
2128     if (bgp->as == as
2129         && ((bgp->name == NULL && name == NULL) 
2130             || (bgp->name && name && strcmp (bgp->name, name) == 0)))
2131       return bgp;
2132   return NULL;
2133 }
2134
2135 /* Lookup BGP structure by view name. */
2136 struct bgp *
2137 bgp_lookup_by_name (const char *name)
2138 {
2139   struct bgp *bgp;
2140   struct listnode *node, *nnode;
2141
2142   for (ALL_LIST_ELEMENTS (bm->bgp, node, nnode, bgp))
2143     if ((bgp->name == NULL && name == NULL)
2144         || (bgp->name && name && strcmp (bgp->name, name) == 0))
2145       return bgp;
2146   return NULL;
2147 }
2148
2149 /* Called from VTY commands. */
2150 int
2151 bgp_get (struct bgp **bgp_val, as_t *as, const char *name)
2152 {
2153   struct bgp *bgp;
2154
2155   /* Multiple instance check. */
2156   if (bgp_option_check (BGP_OPT_MULTIPLE_INSTANCE))
2157     {
2158       if (name)
2159         bgp = bgp_lookup_by_name (name);
2160       else
2161         bgp = bgp_get_default ();
2162
2163       /* Already exists. */
2164       if (bgp)
2165         {
2166           if (bgp->as != *as)
2167             {
2168               *as = bgp->as;
2169               return BGP_ERR_INSTANCE_MISMATCH;
2170             }
2171           *bgp_val = bgp;
2172           return 0;
2173         }
2174     }
2175   else
2176     {
2177       /* BGP instance name can not be specified for single instance.  */
2178       if (name)
2179         return BGP_ERR_MULTIPLE_INSTANCE_NOT_SET;
2180
2181       /* Get default BGP structure if exists. */
2182       bgp = bgp_get_default ();
2183
2184       if (bgp)
2185         {
2186           if (bgp->as != *as)
2187             {
2188               *as = bgp->as;
2189               return BGP_ERR_AS_MISMATCH;
2190             }
2191           *bgp_val = bgp;
2192           return 0;
2193         }
2194     }
2195
2196   bgp = bgp_create (as, name);
2197   bgp_router_id_set(bgp, &router_id_zebra);
2198   *bgp_val = bgp;
2199
2200   /* Create BGP server socket, if first instance.  */
2201   if (list_isempty(bm->bgp)
2202       && !bgp_option_check (BGP_OPT_NO_LISTEN))
2203     {
2204       if (bgp_socket (bm->port, bm->address) < 0)
2205         return BGP_ERR_INVALID_VALUE;
2206     }
2207
2208   listnode_add (bm->bgp, bgp);
2209
2210   return 0;
2211 }
2212
2213 /* Delete BGP instance. */
2214 int
2215 bgp_delete (struct bgp *bgp)
2216 {
2217   struct peer *peer;
2218   struct peer_group *group;
2219   struct listnode *node, *pnode;
2220   struct listnode *next, *pnext;
2221   afi_t afi;
2222   int i;
2223
2224   SET_FLAG(bgp->flags, BGP_FLAG_DELETING);
2225
2226   THREAD_OFF (bgp->t_startup);
2227
2228   for (ALL_LIST_ELEMENTS (bgp->peer, node, next, peer))
2229     {
2230       if (peer->status == Established ||
2231           peer->status == OpenSent ||
2232           peer->status == OpenConfirm)
2233         {
2234             bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2235                              BGP_NOTIFY_CEASE_PEER_UNCONFIG);
2236         }
2237     }
2238
2239   /* Delete static route. */
2240   bgp_static_delete (bgp);
2241
2242   /* Unset redistribution. */
2243   for (afi = AFI_IP; afi < AFI_MAX; afi++)
2244     for (i = 0; i < ZEBRA_ROUTE_MAX; i++) 
2245       if (i != ZEBRA_ROUTE_BGP)
2246         bgp_redistribute_unset (bgp, afi, i);
2247
2248   for (ALL_LIST_ELEMENTS (bgp->peer, node, next, peer))
2249     {
2250       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2251         {
2252           /* Send notify to remote peer. */
2253           bgp_notify_send (peer, BGP_NOTIFY_CEASE, BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN);
2254         }
2255
2256       peer_delete (peer);
2257     }
2258
2259   for (ALL_LIST_ELEMENTS (bgp->group, node, next, group))
2260     {
2261       for (ALL_LIST_ELEMENTS (group->peer, pnode, pnext, peer))
2262         {
2263           if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2264             {
2265               /* Send notify to remote peer. */
2266               bgp_notify_send (peer, BGP_NOTIFY_CEASE, BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN);
2267             }
2268         }
2269       peer_group_delete (group);
2270     }
2271
2272   assert (listcount (bgp->rsclient) == 0);
2273
2274   if (bgp->peer_self) {
2275     peer_delete(bgp->peer_self);
2276     bgp->peer_self = NULL;
2277   }
2278
2279   /*
2280    * Free pending deleted routes. Unfortunately, it also has to process
2281    * all the pending activity for other instances of struct bgp.
2282    *
2283    * This call was added to achieve clean memory allocation at exit,
2284    * for the sake of valgrind.
2285    */
2286   bgp_process_queues_drain_immediate();
2287
2288   /* Remove visibility via the master list - there may however still be
2289    * routes to be processed still referencing the struct bgp.
2290    */
2291   listnode_delete (bm->bgp, bgp);
2292   if (list_isempty(bm->bgp))
2293     bgp_close ();
2294
2295   bgp_unlock(bgp);  /* initial reference */
2296   
2297   return 0;
2298 }
2299
2300 static void bgp_free (struct bgp *);
2301
2302 void
2303 bgp_lock (struct bgp *bgp)
2304 {
2305   ++bgp->lock;
2306 }
2307
2308 void
2309 bgp_unlock(struct bgp *bgp)
2310 {
2311   assert(bgp->lock > 0);
2312   if (--bgp->lock == 0)
2313     bgp_free (bgp);
2314 }
2315
2316 static void
2317 bgp_free (struct bgp *bgp)
2318 {
2319   afi_t afi;
2320   safi_t safi;
2321
2322   list_delete (bgp->group);
2323   list_delete (bgp->peer);
2324   list_delete (bgp->rsclient);
2325
2326   if (bgp->name)
2327     free (bgp->name);
2328   
2329   for (afi = AFI_IP; afi < AFI_MAX; afi++)
2330     for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
2331       {
2332         if (bgp->route[afi][safi])
2333           bgp_table_finish (&bgp->route[afi][safi]);
2334         if (bgp->aggregate[afi][safi])
2335           bgp_table_finish (&bgp->aggregate[afi][safi]) ;
2336         if (bgp->rib[afi][safi])
2337           bgp_table_finish (&bgp->rib[afi][safi]);
2338       }
2339   XFREE (MTYPE_BGP, bgp);
2340 }
2341
2342 struct peer *
2343 peer_lookup (struct bgp *bgp, union sockunion *su)
2344 {
2345   struct peer *peer;
2346   struct listnode *node, *nnode;
2347
2348   if (bgp != NULL)
2349     {
2350       for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
2351         if (sockunion_same (&peer->su, su)
2352             && ! CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
2353           return peer;
2354     }
2355   else if (bm->bgp != NULL)
2356     {
2357       struct listnode *bgpnode, *nbgpnode;
2358   
2359       for (ALL_LIST_ELEMENTS (bm->bgp, bgpnode, nbgpnode, bgp))
2360         for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
2361           if (sockunion_same (&peer->su, su)
2362               && ! CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
2363             return peer;
2364     }
2365   return NULL;
2366 }
2367
2368 struct peer *
2369 peer_lookup_with_open (union sockunion *su, as_t remote_as,
2370                        struct in_addr *remote_id, int *as)
2371 {
2372   struct peer *peer;
2373   struct listnode *node;
2374   struct listnode *bgpnode;
2375   struct bgp *bgp;
2376
2377   if (! bm->bgp)
2378     return NULL;
2379
2380   for (ALL_LIST_ELEMENTS_RO (bm->bgp, bgpnode, bgp))
2381     {
2382       for (ALL_LIST_ELEMENTS_RO (bgp->peer, node, peer))
2383         {
2384           if (sockunion_same (&peer->su, su)
2385               && ! CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
2386             {
2387               if (peer->as == remote_as
2388                   && peer->remote_id.s_addr == remote_id->s_addr)
2389                 return peer;
2390               if (peer->as == remote_as)
2391                 *as = 1;
2392             }
2393         }
2394
2395       for (ALL_LIST_ELEMENTS_RO (bgp->peer, node, peer))
2396         {
2397           if (sockunion_same (&peer->su, su)
2398               &&  ! CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
2399             {
2400               if (peer->as == remote_as
2401                   && peer->remote_id.s_addr == 0)
2402                 return peer;
2403               if (peer->as == remote_as)
2404                 *as = 1;
2405             }
2406         }
2407     }
2408   return NULL;
2409 }
2410
2411 /* If peer is configured at least one address family return 1. */
2412 int
2413 peer_active (struct peer *peer)
2414 {
2415   if (peer->afc[AFI_IP][SAFI_UNICAST]
2416       || peer->afc[AFI_IP][SAFI_MULTICAST]
2417       || peer->afc[AFI_IP][SAFI_MPLS_VPN]
2418       || peer->afc[AFI_IP][SAFI_ENCAP]
2419       || peer->afc[AFI_IP6][SAFI_UNICAST]
2420       || peer->afc[AFI_IP6][SAFI_MULTICAST]
2421       || peer->afc[AFI_IP6][SAFI_MPLS_VPN]
2422       || peer->afc[AFI_IP6][SAFI_ENCAP])
2423     return 1;
2424   return 0;
2425 }
2426
2427 /* If peer is negotiated at least one address family return 1. */
2428 int
2429 peer_active_nego (struct peer *peer)
2430 {
2431   if (peer->afc_nego[AFI_IP][SAFI_UNICAST]
2432       || peer->afc_nego[AFI_IP][SAFI_MULTICAST]
2433       || peer->afc_nego[AFI_IP][SAFI_MPLS_VPN]
2434       || peer->afc_nego[AFI_IP][SAFI_ENCAP]
2435       || peer->afc_nego[AFI_IP6][SAFI_UNICAST]
2436       || peer->afc_nego[AFI_IP6][SAFI_MULTICAST]
2437       || peer->afc_nego[AFI_IP6][SAFI_MPLS_VPN]
2438       || peer->afc_nego[AFI_IP6][SAFI_ENCAP])
2439     return 1;
2440   return 0;
2441 }
2442
2443 /* peer_flag_change_type. */
2444 enum peer_change_type
2445 {
2446   peer_change_none,
2447   peer_change_reset,
2448   peer_change_reset_in,
2449   peer_change_reset_out,
2450 };
2451
2452 static void
2453 peer_change_action (struct peer *peer, afi_t afi, safi_t safi,
2454                     enum peer_change_type type)
2455 {
2456   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2457     return;
2458
2459   if (peer->status != Established)
2460     return;
2461
2462   if (type == peer_change_reset)
2463     bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2464                      BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2465   else if (type == peer_change_reset_in)
2466     {
2467       if (CHECK_FLAG (peer->cap, PEER_CAP_REFRESH_OLD_RCV)
2468           || CHECK_FLAG (peer->cap, PEER_CAP_REFRESH_NEW_RCV))
2469         bgp_route_refresh_send (peer, afi, safi, 0, 0, 0);
2470       else
2471         bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2472                          BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2473     }
2474   else if (type == peer_change_reset_out)
2475     bgp_announce_route (peer, afi, safi);
2476 }
2477
2478 struct peer_flag_action
2479 {
2480   /* Peer's flag.  */
2481   u_int32_t flag;
2482
2483   /* This flag can be set for peer-group member.  */
2484   u_char not_for_member;
2485
2486   /* Action when the flag is changed.  */
2487   enum peer_change_type type;
2488
2489   /* Peer down cause */
2490   u_char peer_down;
2491 };
2492
2493 static const struct peer_flag_action peer_flag_action_list[] =
2494   {
2495     { PEER_FLAG_PASSIVE,                  0, peer_change_reset },
2496     { PEER_FLAG_SHUTDOWN,                 0, peer_change_reset },
2497     { PEER_FLAG_DONT_CAPABILITY,          0, peer_change_none },
2498     { PEER_FLAG_OVERRIDE_CAPABILITY,      0, peer_change_none },
2499     { PEER_FLAG_STRICT_CAP_MATCH,         0, peer_change_none },
2500     { PEER_FLAG_DYNAMIC_CAPABILITY,       0, peer_change_reset },
2501     { PEER_FLAG_DISABLE_CONNECTED_CHECK,  0, peer_change_reset },
2502     { 0, 0, 0 }
2503   };
2504
2505 static const struct peer_flag_action peer_af_flag_action_list[] =
2506   {
2507     { PEER_FLAG_NEXTHOP_SELF,             1, peer_change_reset_out },
2508     { PEER_FLAG_SEND_COMMUNITY,           1, peer_change_reset_out },
2509     { PEER_FLAG_SEND_EXT_COMMUNITY,       1, peer_change_reset_out },
2510     { PEER_FLAG_SEND_LARGE_COMMUNITY,     1, peer_change_reset_out },
2511     { PEER_FLAG_SOFT_RECONFIG,            0, peer_change_reset_in },
2512     { PEER_FLAG_REFLECTOR_CLIENT,         1, peer_change_reset },
2513     { PEER_FLAG_RSERVER_CLIENT,           1, peer_change_reset },
2514     { PEER_FLAG_AS_PATH_UNCHANGED,        1, peer_change_reset_out },
2515     { PEER_FLAG_NEXTHOP_UNCHANGED,        1, peer_change_reset_out },
2516     { PEER_FLAG_MED_UNCHANGED,            1, peer_change_reset_out },
2517     { PEER_FLAG_REMOVE_PRIVATE_AS,        1, peer_change_reset_out },
2518     { PEER_FLAG_ALLOWAS_IN,               0, peer_change_reset_in },
2519     { PEER_FLAG_ORF_PREFIX_SM,            1, peer_change_reset },
2520     { PEER_FLAG_ORF_PREFIX_RM,            1, peer_change_reset },
2521     { PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED,  0, peer_change_reset_out },
2522     { PEER_FLAG_NEXTHOP_SELF_ALL,         1, peer_change_reset_out },
2523     { 0, 0, 0 }
2524   };
2525
2526 /* Proper action set. */
2527 static int
2528 peer_flag_action_set (const struct peer_flag_action *action_list, int size,
2529                       struct peer_flag_action *action, u_int32_t flag)
2530 {
2531   int i;
2532   int found = 0;
2533   int reset_in = 0;
2534   int reset_out = 0;
2535   const struct peer_flag_action *match = NULL;
2536
2537   /* Check peer's frag action.  */
2538   for (i = 0; i < size; i++)
2539     {
2540       match = &action_list[i];
2541
2542       if (match->flag == 0)
2543         break;
2544
2545       if (match->flag & flag)
2546         {
2547           found = 1;
2548
2549           if (match->type == peer_change_reset_in)
2550             reset_in = 1;
2551           if (match->type == peer_change_reset_out)
2552             reset_out = 1;
2553           if (match->type == peer_change_reset)
2554             {
2555               reset_in = 1;
2556               reset_out = 1;
2557             }
2558           if (match->not_for_member)
2559             action->not_for_member = 1;
2560         }
2561     }
2562
2563   /* Set peer clear type.  */
2564   if (reset_in && reset_out)
2565     action->type = peer_change_reset;
2566   else if (reset_in)
2567     action->type = peer_change_reset_in;
2568   else if (reset_out)
2569     action->type = peer_change_reset_out;
2570   else
2571     action->type = peer_change_none;
2572
2573   return found;
2574 }
2575
2576 static void
2577 peer_flag_modify_action (struct peer *peer, u_int32_t flag)
2578 {
2579   if (flag == PEER_FLAG_SHUTDOWN)
2580     {
2581       if (CHECK_FLAG (peer->flags, flag))
2582         {
2583           if (CHECK_FLAG (peer->sflags, PEER_STATUS_NSF_WAIT))
2584             peer_nsf_stop (peer);
2585
2586           UNSET_FLAG (peer->sflags, PEER_STATUS_PREFIX_OVERFLOW);
2587           if (peer->t_pmax_restart)
2588             {
2589               BGP_TIMER_OFF (peer->t_pmax_restart);
2590               if (BGP_DEBUG (events, EVENTS))
2591                 zlog_debug ("%s Maximum-prefix restart timer canceled",
2592                             peer->host);
2593             }
2594
2595       if (CHECK_FLAG (peer->sflags, PEER_STATUS_NSF_WAIT))
2596         peer_nsf_stop (peer);
2597
2598           if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2599             bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2600                              BGP_NOTIFY_CEASE_ADMIN_SHUTDOWN);
2601           else
2602             BGP_EVENT_ADD (peer, BGP_Stop);
2603         }
2604       else
2605         {
2606           peer->v_start = BGP_INIT_START_TIMER;
2607           BGP_EVENT_ADD (peer, BGP_Stop);
2608         }
2609     }
2610   else if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2611     {
2612       if (flag == PEER_FLAG_DYNAMIC_CAPABILITY)
2613         peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
2614       else if (flag == PEER_FLAG_PASSIVE)
2615         peer->last_reset = PEER_DOWN_PASSIVE_CHANGE;
2616       else if (flag == PEER_FLAG_DISABLE_CONNECTED_CHECK)
2617         peer->last_reset = PEER_DOWN_MULTIHOP_CHANGE;
2618
2619       bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2620                        BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2621     }
2622   else
2623     BGP_EVENT_ADD (peer, BGP_Stop);
2624 }
2625
2626 /* Change specified peer flag. */
2627 static int
2628 peer_flag_modify (struct peer *peer, u_int32_t flag, int set)
2629 {
2630   int found;
2631   int size;
2632   struct peer_group *group;
2633   struct listnode *node, *nnode;
2634   struct peer_flag_action action;
2635
2636   memset (&action, 0, sizeof (struct peer_flag_action));
2637   size = sizeof peer_flag_action_list / sizeof (struct peer_flag_action);
2638
2639   found = peer_flag_action_set (peer_flag_action_list, size, &action, flag);
2640
2641   /* No flag action is found.  */
2642   if (! found)
2643     return BGP_ERR_INVALID_FLAG;    
2644
2645   /* Not for peer-group member.  */
2646   if (action.not_for_member && peer_group_active (peer))
2647     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
2648
2649   /* When unset the peer-group member's flag we have to check
2650      peer-group configuration.  */
2651   if (! set && peer_group_active (peer))
2652     if (CHECK_FLAG (peer->group->conf->flags, flag))
2653       {
2654         if (flag == PEER_FLAG_SHUTDOWN)
2655           return BGP_ERR_PEER_GROUP_SHUTDOWN;
2656         else
2657           return BGP_ERR_PEER_GROUP_HAS_THE_FLAG;
2658       }
2659
2660   /* Flag conflict check.  */
2661   if (set
2662       && CHECK_FLAG (peer->flags | flag, PEER_FLAG_STRICT_CAP_MATCH)
2663       && CHECK_FLAG (peer->flags | flag, PEER_FLAG_OVERRIDE_CAPABILITY))
2664     return BGP_ERR_PEER_FLAG_CONFLICT;
2665
2666   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2667     {
2668       if (set && CHECK_FLAG (peer->flags, flag) == flag)
2669         return 0;
2670       if (! set && ! CHECK_FLAG (peer->flags, flag))
2671         return 0;
2672     }
2673
2674   if (set)
2675     SET_FLAG (peer->flags, flag);
2676   else
2677     UNSET_FLAG (peer->flags, flag);
2678  
2679   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2680     {
2681       if (action.type == peer_change_reset)
2682         peer_flag_modify_action (peer, flag);
2683
2684       return 0;
2685     }
2686
2687   /* peer-group member updates. */
2688   group = peer->group;
2689
2690   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
2691     {
2692       if (set && CHECK_FLAG (peer->flags, flag) == flag)
2693         continue;
2694
2695       if (! set && ! CHECK_FLAG (peer->flags, flag))
2696         continue;
2697
2698       if (set)
2699         SET_FLAG (peer->flags, flag);
2700       else
2701         UNSET_FLAG (peer->flags, flag);
2702
2703       if (action.type == peer_change_reset)
2704         peer_flag_modify_action (peer, flag);
2705     }
2706   return 0;
2707 }
2708
2709 int
2710 peer_flag_set (struct peer *peer, u_int32_t flag)
2711 {
2712   return peer_flag_modify (peer, flag, 1);
2713 }
2714
2715 int
2716 peer_flag_unset (struct peer *peer, u_int32_t flag)
2717 {
2718   return peer_flag_modify (peer, flag, 0);
2719 }
2720
2721 static int
2722 peer_is_group_member (struct peer *peer, afi_t afi, safi_t safi)
2723 {
2724   if (peer->af_group[afi][safi])
2725     return 1;
2726   return 0;
2727 }
2728
2729 static int
2730 peer_af_flag_modify (struct peer *peer, afi_t afi, safi_t safi, u_int32_t flag,
2731                      int set)
2732 {
2733   int found;
2734   int size;
2735   struct listnode *node, *nnode;
2736   struct peer_group *group;
2737   struct peer_flag_action action;
2738
2739   memset (&action, 0, sizeof (struct peer_flag_action));
2740   size = sizeof peer_af_flag_action_list / sizeof (struct peer_flag_action);
2741   
2742   found = peer_flag_action_set (peer_af_flag_action_list, size, &action, flag);
2743   
2744   /* No flag action is found.  */
2745   if (! found)
2746     return BGP_ERR_INVALID_FLAG;    
2747
2748   /* Adress family must be activated.  */
2749   if (! peer->afc[afi][safi])
2750     return BGP_ERR_PEER_INACTIVE;
2751
2752   /* Not for peer-group member.  */
2753   if (action.not_for_member && peer_is_group_member (peer, afi, safi))
2754     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
2755
2756  /* Spcecial check for reflector client.  */
2757   if (flag & PEER_FLAG_REFLECTOR_CLIENT
2758       && peer_sort (peer) != BGP_PEER_IBGP)
2759     return BGP_ERR_NOT_INTERNAL_PEER;
2760
2761   /* Spcecial check for remove-private-AS.  */
2762   if (flag & PEER_FLAG_REMOVE_PRIVATE_AS
2763       && peer_sort (peer) == BGP_PEER_IBGP)
2764     return BGP_ERR_REMOVE_PRIVATE_AS;
2765
2766   /* When unset the peer-group member's flag we have to check
2767      peer-group configuration.  */
2768   if (! set && peer->af_group[afi][safi])
2769     if (CHECK_FLAG (peer->group->conf->af_flags[afi][safi], flag))
2770       return BGP_ERR_PEER_GROUP_HAS_THE_FLAG;
2771
2772   /* When current flag configuration is same as requested one.  */
2773   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2774     {
2775       if (set && CHECK_FLAG (peer->af_flags[afi][safi], flag) == flag)
2776         return 0;
2777       if (! set && ! CHECK_FLAG (peer->af_flags[afi][safi], flag))
2778         return 0;
2779     }
2780
2781   if (set)
2782     SET_FLAG (peer->af_flags[afi][safi], flag);
2783   else
2784     UNSET_FLAG (peer->af_flags[afi][safi], flag);
2785
2786   /* Execute action when peer is established.  */
2787   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP)
2788       && peer->status == Established)
2789     {
2790       if (! set && flag == PEER_FLAG_SOFT_RECONFIG)
2791         bgp_clear_adj_in (peer, afi, safi);
2792       else
2793        {
2794          if (flag == PEER_FLAG_REFLECTOR_CLIENT)
2795            peer->last_reset = PEER_DOWN_RR_CLIENT_CHANGE;
2796          else if (flag == PEER_FLAG_RSERVER_CLIENT)
2797            peer->last_reset = PEER_DOWN_RS_CLIENT_CHANGE;
2798          else if (flag == PEER_FLAG_ORF_PREFIX_SM)
2799            peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
2800          else if (flag == PEER_FLAG_ORF_PREFIX_RM)
2801            peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
2802
2803          peer_change_action (peer, afi, safi, action.type);
2804        }
2805
2806     }
2807
2808   /* Peer group member updates.  */
2809   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2810     {
2811       group = peer->group;
2812       
2813       for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
2814         {
2815           if (! peer->af_group[afi][safi])
2816             continue;
2817
2818           if (set && CHECK_FLAG (peer->af_flags[afi][safi], flag) == flag)
2819             continue;
2820
2821           if (! set && ! CHECK_FLAG (peer->af_flags[afi][safi], flag))
2822             continue;
2823
2824           if (set)
2825             SET_FLAG (peer->af_flags[afi][safi], flag);
2826           else
2827             UNSET_FLAG (peer->af_flags[afi][safi], flag);
2828
2829           if (peer->status == Established)
2830             {
2831               if (! set && flag == PEER_FLAG_SOFT_RECONFIG)
2832                 bgp_clear_adj_in (peer, afi, safi);
2833               else
2834                {
2835                  if (flag == PEER_FLAG_REFLECTOR_CLIENT)
2836                    peer->last_reset = PEER_DOWN_RR_CLIENT_CHANGE;
2837                  else if (flag == PEER_FLAG_RSERVER_CLIENT)
2838                    peer->last_reset = PEER_DOWN_RS_CLIENT_CHANGE;
2839                  else if (flag == PEER_FLAG_ORF_PREFIX_SM)
2840                    peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
2841                  else if (flag == PEER_FLAG_ORF_PREFIX_RM)
2842                    peer->last_reset = PEER_DOWN_CAPABILITY_CHANGE;
2843
2844                  peer_change_action (peer, afi, safi, action.type);
2845                }
2846             }
2847         }
2848     }
2849   return 0;
2850 }
2851
2852 int
2853 peer_af_flag_set (struct peer *peer, afi_t afi, safi_t safi, u_int32_t flag)
2854 {
2855   return peer_af_flag_modify (peer, afi, safi, flag, 1);
2856 }
2857
2858 int
2859 peer_af_flag_unset (struct peer *peer, afi_t afi, safi_t safi, u_int32_t flag)
2860 {
2861   return peer_af_flag_modify (peer, afi, safi, flag, 0);
2862 }
2863
2864 /* EBGP multihop configuration. */
2865 int
2866 peer_ebgp_multihop_set (struct peer *peer, int ttl)
2867 {
2868   struct peer_group *group;
2869   struct listnode *node, *nnode;
2870   struct peer *peer1;
2871
2872   if (peer->sort == BGP_PEER_IBGP)
2873     return BGP_ERR_NO_IBGP_WITH_TTLHACK;
2874
2875   if (peer->gtsm_hops != 0)
2876     return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
2877
2878   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2879     {
2880       group = peer->group;
2881       for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer1))
2882         {
2883           if (peer1->gtsm_hops != 0)
2884             return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
2885         }
2886     }
2887
2888   peer->ttl = ttl;
2889
2890   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2891     {
2892       bgp_set_socket_ttl (peer, peer->fd);
2893     }
2894   else
2895     {
2896       group = peer->group;
2897       for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
2898         {
2899           peer->ttl = ttl;
2900           bgp_set_socket_ttl (peer, peer->fd);
2901         }
2902     }
2903
2904   return 0;
2905 }
2906
2907 /* Neighbor description. */
2908 int
2909 peer_description_set (struct peer *peer, const char *desc)
2910 {
2911   if (peer->desc)
2912     XFREE (MTYPE_PEER_DESC, peer->desc);
2913
2914   peer->desc = XSTRDUP (MTYPE_PEER_DESC, desc);
2915
2916   return 0;
2917 }
2918
2919 int
2920 peer_description_unset (struct peer *peer)
2921 {
2922   if (peer->desc)
2923     XFREE (MTYPE_PEER_DESC, peer->desc);
2924
2925   peer->desc = NULL;
2926
2927   return 0;
2928 }
2929
2930 /* Neighbor update-source. */
2931 int
2932 peer_update_source_if_set (struct peer *peer, const char *ifname)
2933 {
2934   struct peer_group *group;
2935   struct listnode *node, *nnode;
2936
2937   if (peer->update_if)
2938     {
2939       if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP)
2940           && strcmp (peer->update_if, ifname) == 0)
2941         return 0;
2942
2943       XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
2944       peer->update_if = NULL;
2945     }
2946
2947   if (peer->update_source)
2948     {
2949       sockunion_free (peer->update_source);
2950       peer->update_source = NULL;
2951     }
2952
2953   peer->update_if = XSTRDUP (MTYPE_PEER_UPDATE_SOURCE, ifname);
2954
2955   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
2956     {
2957       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2958        {
2959          peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
2960          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2961                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2962        }
2963       else
2964         BGP_EVENT_ADD (peer, BGP_Stop);
2965       return 0;
2966     }
2967
2968   /* peer-group member updates. */
2969   group = peer->group;
2970   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
2971     {
2972       if (peer->update_if)
2973         {
2974           if (strcmp (peer->update_if, ifname) == 0)
2975             continue;
2976
2977           XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
2978           peer->update_if = NULL;
2979         }
2980
2981       if (peer->update_source)
2982         {
2983           sockunion_free (peer->update_source);
2984           peer->update_source = NULL;
2985         }
2986
2987       peer->update_if = XSTRDUP (MTYPE_PEER_UPDATE_SOURCE, ifname);
2988
2989       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
2990        {
2991          peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
2992          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
2993                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
2994        }
2995       else
2996         BGP_EVENT_ADD (peer, BGP_Stop);
2997     }
2998   return 0;
2999 }
3000
3001 int
3002 peer_update_source_addr_set (struct peer *peer, const union sockunion *su)
3003 {
3004   struct peer_group *group;
3005   struct listnode *node, *nnode;
3006
3007   if (peer->update_source)
3008     {
3009       if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP)
3010           && sockunion_cmp (peer->update_source, su) == 0)
3011         return 0;
3012       sockunion_free (peer->update_source);
3013       peer->update_source = NULL;
3014     }
3015
3016   if (peer->update_if)
3017     {
3018       XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
3019       peer->update_if = NULL;
3020     }
3021
3022   peer->update_source = sockunion_dup (su);
3023
3024   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3025     {
3026       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3027        {
3028          peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
3029          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3030                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3031        }
3032       else
3033         BGP_EVENT_ADD (peer, BGP_Stop);
3034       return 0;
3035     }
3036
3037   /* peer-group member updates. */
3038   group = peer->group;
3039   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3040     {
3041       if (peer->update_source)
3042         {
3043           if (sockunion_cmp (peer->update_source, su) == 0)
3044             continue;
3045           sockunion_free (peer->update_source);
3046           peer->update_source = NULL;
3047         }
3048
3049       if (peer->update_if)
3050         {
3051           XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
3052           peer->update_if = NULL;
3053         }
3054
3055       peer->update_source = sockunion_dup (su);
3056
3057       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3058        {
3059          peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
3060          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3061                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3062        }
3063       else
3064         BGP_EVENT_ADD (peer, BGP_Stop);
3065     }
3066   return 0;
3067 }
3068
3069 int
3070 peer_update_source_unset (struct peer *peer)
3071 {
3072   union sockunion *su;
3073   struct peer_group *group;
3074   struct listnode *node, *nnode;
3075
3076   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP)
3077       && ! peer->update_source
3078       && ! peer->update_if)
3079     return 0;
3080
3081   if (peer->update_source)
3082     {
3083       sockunion_free (peer->update_source);
3084       peer->update_source = NULL;
3085     }
3086   if (peer->update_if)
3087     {
3088       XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
3089       peer->update_if = NULL;
3090     }
3091
3092   if (peer_group_active (peer))
3093     {
3094       group = peer->group;
3095
3096       if (group->conf->update_source)
3097         {
3098           su = sockunion_dup (group->conf->update_source);
3099           peer->update_source = su;
3100         }
3101       else if (group->conf->update_if)
3102         peer->update_if = 
3103           XSTRDUP (MTYPE_PEER_UPDATE_SOURCE, group->conf->update_if);
3104     }
3105
3106   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3107     {
3108       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3109        {
3110          peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
3111          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3112                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3113        }
3114       else
3115         BGP_EVENT_ADD (peer, BGP_Stop);
3116       return 0;
3117     }
3118
3119   /* peer-group member updates. */
3120   group = peer->group;
3121   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3122     {
3123       if (! peer->update_source && ! peer->update_if)
3124         continue;
3125
3126       if (peer->update_source)
3127         {
3128           sockunion_free (peer->update_source);
3129           peer->update_source = NULL;
3130         }
3131
3132       if (peer->update_if)
3133         {
3134           XFREE (MTYPE_PEER_UPDATE_SOURCE, peer->update_if);
3135           peer->update_if = NULL;
3136         }
3137
3138       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3139        {
3140          peer->last_reset = PEER_DOWN_UPDATE_SOURCE_CHANGE;
3141          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3142                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3143        }
3144       else
3145         BGP_EVENT_ADD (peer, BGP_Stop);
3146     }
3147   return 0;
3148 }
3149
3150 int
3151 peer_default_originate_set (struct peer *peer, afi_t afi, safi_t safi,
3152                             const char *rmap)
3153 {
3154   struct peer_group *group;
3155   struct listnode *node, *nnode;
3156
3157   /* Adress family must be activated.  */
3158   if (! peer->afc[afi][safi])
3159     return BGP_ERR_PEER_INACTIVE;
3160
3161   /* Default originate can't be used for peer group memeber.  */
3162   if (peer_is_group_member (peer, afi, safi))
3163     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3164
3165   if (! CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_DEFAULT_ORIGINATE)
3166       || (rmap && ! peer->default_rmap[afi][safi].name)
3167       || (rmap && strcmp (rmap, peer->default_rmap[afi][safi].name) != 0))
3168     { 
3169       SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_DEFAULT_ORIGINATE);
3170
3171       if (rmap)
3172         {
3173           if (peer->default_rmap[afi][safi].name)
3174             free (peer->default_rmap[afi][safi].name);
3175           peer->default_rmap[afi][safi].name = strdup (rmap);
3176           peer->default_rmap[afi][safi].map = route_map_lookup_by_name (rmap);
3177         }
3178     }
3179
3180   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3181     {
3182       if (peer->status == Established && peer->afc_nego[afi][safi])
3183         bgp_default_originate (peer, afi, safi, 0);
3184       return 0;
3185     }
3186
3187   /* peer-group member updates. */
3188   group = peer->group;
3189   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3190     {
3191       SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_DEFAULT_ORIGINATE);
3192
3193       if (rmap)
3194         {
3195           if (peer->default_rmap[afi][safi].name)
3196             free (peer->default_rmap[afi][safi].name);
3197           peer->default_rmap[afi][safi].name = strdup (rmap);
3198           peer->default_rmap[afi][safi].map = route_map_lookup_by_name (rmap);
3199         }
3200
3201       if (peer->status == Established && peer->afc_nego[afi][safi])
3202         bgp_default_originate (peer, afi, safi, 0);
3203     }
3204   return 0;
3205 }
3206
3207 int
3208 peer_default_originate_unset (struct peer *peer, afi_t afi, safi_t safi)
3209 {
3210   struct peer_group *group;
3211   struct listnode *node, *nnode;
3212
3213   /* Adress family must be activated.  */
3214   if (! peer->afc[afi][safi])
3215     return BGP_ERR_PEER_INACTIVE;
3216
3217   /* Default originate can't be used for peer group memeber.  */
3218   if (peer_is_group_member (peer, afi, safi))
3219     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3220
3221   if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_DEFAULT_ORIGINATE))
3222     { 
3223       UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_DEFAULT_ORIGINATE);
3224
3225       if (peer->default_rmap[afi][safi].name)
3226         free (peer->default_rmap[afi][safi].name);
3227       peer->default_rmap[afi][safi].name = NULL;
3228       peer->default_rmap[afi][safi].map = NULL;
3229     }
3230
3231   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3232     {
3233       if (peer->status == Established && peer->afc_nego[afi][safi])
3234         bgp_default_originate (peer, afi, safi, 1);
3235       return 0;
3236     }
3237
3238   /* peer-group member updates. */
3239   group = peer->group;
3240   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3241     {
3242       UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_DEFAULT_ORIGINATE);
3243
3244       if (peer->default_rmap[afi][safi].name)
3245         free (peer->default_rmap[afi][safi].name);
3246       peer->default_rmap[afi][safi].name = NULL;
3247       peer->default_rmap[afi][safi].map = NULL;
3248
3249       if (peer->status == Established && peer->afc_nego[afi][safi])
3250         bgp_default_originate (peer, afi, safi, 1);
3251     }
3252   return 0;
3253 }
3254
3255 int
3256 peer_port_set (struct peer *peer, u_int16_t port)
3257 {
3258   peer->port = port;
3259   return 0;
3260 }
3261
3262 int
3263 peer_port_unset (struct peer *peer)
3264 {
3265   peer->port = BGP_PORT_DEFAULT;
3266   return 0;
3267 }
3268
3269 /* neighbor weight. */
3270 int
3271 peer_weight_set (struct peer *peer, u_int16_t weight)
3272 {
3273   struct peer_group *group;
3274   struct listnode *node, *nnode;
3275
3276   SET_FLAG (peer->config, PEER_CONFIG_WEIGHT);
3277   peer->weight = weight;
3278
3279   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3280     return 0;
3281
3282   /* peer-group member updates. */
3283   group = peer->group;
3284   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3285     {
3286       peer->weight = group->conf->weight;
3287     }
3288   return 0;
3289 }
3290
3291 int
3292 peer_weight_unset (struct peer *peer)
3293 {
3294   struct peer_group *group;
3295   struct listnode *node, *nnode;
3296
3297   /* Set default weight. */
3298   if (peer_group_active (peer))
3299     peer->weight = peer->group->conf->weight;
3300   else
3301     peer->weight = 0;
3302
3303   UNSET_FLAG (peer->config, PEER_CONFIG_WEIGHT);
3304
3305   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3306     return 0;
3307
3308   /* peer-group member updates. */
3309   group = peer->group;
3310   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3311     {
3312       peer->weight = 0;
3313     }
3314   return 0;
3315 }
3316
3317 int
3318 peer_timers_set (struct peer *peer, u_int32_t keepalive, u_int32_t holdtime)
3319 {
3320   struct peer_group *group;
3321   struct listnode *node, *nnode;
3322
3323   /* Not for peer group memeber.  */
3324   if (peer_group_active (peer))
3325     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3326
3327   /* keepalive value check.  */
3328   if (keepalive > 65535)
3329     return BGP_ERR_INVALID_VALUE;
3330
3331   /* Holdtime value check.  */
3332   if (holdtime > 65535)
3333     return BGP_ERR_INVALID_VALUE;
3334
3335   /* Holdtime value must be either 0 or greater than 3.  */
3336   if (holdtime < 3 && holdtime != 0)
3337     return BGP_ERR_INVALID_VALUE;
3338
3339   /* Set value to the configuration. */
3340   SET_FLAG (peer->config, PEER_CONFIG_TIMER);
3341   peer->holdtime = holdtime;
3342   peer->keepalive = (keepalive < holdtime / 3 ? keepalive : holdtime / 3);
3343
3344   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3345     return 0;
3346
3347   /* peer-group member updates. */
3348   group = peer->group;
3349   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3350     {
3351       SET_FLAG (peer->config, PEER_CONFIG_TIMER);
3352       peer->holdtime = group->conf->holdtime;
3353       peer->keepalive = group->conf->keepalive;
3354     }
3355   return 0;
3356 }
3357
3358 int
3359 peer_timers_unset (struct peer *peer)
3360 {
3361   struct peer_group *group;
3362   struct listnode *node, *nnode;
3363
3364   if (peer_group_active (peer))
3365     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3366
3367   /* Clear configuration. */
3368   UNSET_FLAG (peer->config, PEER_CONFIG_TIMER);
3369   peer->keepalive = 0;
3370   peer->holdtime = 0;
3371
3372   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3373     return 0;
3374
3375   /* peer-group member updates. */
3376   group = peer->group;
3377   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3378     {
3379       UNSET_FLAG (peer->config, PEER_CONFIG_TIMER);
3380       peer->holdtime = 0;
3381       peer->keepalive = 0;
3382     }
3383
3384   return 0;
3385 }
3386
3387 int
3388 peer_timers_connect_set (struct peer *peer, u_int32_t connect)
3389 {
3390   struct peer_group *group;
3391   struct listnode *node, *nnode;
3392
3393   if (peer_group_active (peer))
3394     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3395
3396   if (connect > 65535)
3397     return BGP_ERR_INVALID_VALUE;
3398
3399   /* Set value to the configuration. */
3400   SET_FLAG (peer->config, PEER_CONFIG_CONNECT);
3401   peer->connect = connect;
3402
3403   /* Set value to timer setting. */
3404   peer->v_connect = connect;
3405
3406   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3407     return 0;
3408
3409   /* peer-group member updates. */
3410   group = peer->group;
3411   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3412     {
3413       SET_FLAG (peer->config, PEER_CONFIG_CONNECT);
3414       peer->connect = connect;
3415       peer->v_connect = connect;
3416     }
3417   return 0;
3418 }
3419
3420 int
3421 peer_timers_connect_unset (struct peer *peer)
3422 {
3423   struct peer_group *group;
3424   struct listnode *node, *nnode;
3425
3426   if (peer_group_active (peer))
3427     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3428
3429   /* Clear configuration. */
3430   UNSET_FLAG (peer->config, PEER_CONFIG_CONNECT);
3431   peer->connect = 0;
3432
3433   /* Set timer setting to default value. */
3434   peer->v_connect = BGP_DEFAULT_CONNECT_RETRY;
3435
3436   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3437     return 0;
3438
3439   /* peer-group member updates. */
3440   group = peer->group;
3441   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3442     {
3443       UNSET_FLAG (peer->config, PEER_CONFIG_CONNECT);
3444       peer->connect = 0;
3445       peer->v_connect = BGP_DEFAULT_CONNECT_RETRY;
3446     }
3447    return 0;
3448 }
3449
3450 int
3451 peer_advertise_interval_set (struct peer *peer, u_int32_t routeadv)
3452 {
3453   struct peer_group *group;
3454   struct listnode *node, *nnode;
3455
3456   if (peer_group_active (peer))
3457     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3458
3459   if (routeadv > 600)
3460     return BGP_ERR_INVALID_VALUE;
3461
3462   SET_FLAG (peer->config, PEER_CONFIG_ROUTEADV);
3463   peer->routeadv = routeadv;
3464   peer->v_routeadv = routeadv;
3465
3466   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3467     return 0;
3468
3469   /* peer-group member updates. */
3470   group = peer->group;
3471   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3472     {
3473       SET_FLAG (peer->config, PEER_CONFIG_ROUTEADV);
3474       peer->routeadv = routeadv;
3475       peer->v_routeadv = routeadv;
3476     }
3477
3478   return 0;
3479 }
3480
3481 int
3482 peer_advertise_interval_unset (struct peer *peer)
3483 {
3484   struct peer_group *group;
3485   struct listnode *node, *nnode;
3486
3487   if (peer_group_active (peer))
3488     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3489
3490   UNSET_FLAG (peer->config, PEER_CONFIG_ROUTEADV);
3491   peer->routeadv = 0;
3492
3493   if (peer->sort == BGP_PEER_IBGP)
3494     peer->v_routeadv = BGP_DEFAULT_IBGP_ROUTEADV;
3495   else
3496     peer->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
3497
3498   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3499     return 0;
3500
3501   /* peer-group member updates. */
3502   group = peer->group;
3503   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3504     {
3505       UNSET_FLAG (peer->config, PEER_CONFIG_ROUTEADV);
3506       peer->routeadv = 0;
3507
3508       if (peer->sort == BGP_PEER_IBGP)
3509         peer->v_routeadv = BGP_DEFAULT_IBGP_ROUTEADV;
3510       else
3511         peer->v_routeadv = BGP_DEFAULT_EBGP_ROUTEADV;
3512     }
3513   
3514   return 0;
3515 }
3516
3517 /* neighbor interface */
3518 int
3519 peer_interface_set (struct peer *peer, const char *str)
3520 {
3521   if (peer->ifname)
3522     free (peer->ifname);
3523   peer->ifname = strdup (str);
3524
3525   return 0;
3526 }
3527
3528 int
3529 peer_interface_unset (struct peer *peer)
3530 {
3531   if (peer->ifname)
3532     free (peer->ifname);
3533   peer->ifname = NULL;
3534
3535   return 0;
3536 }
3537
3538 /* Allow-as in.  */
3539 int
3540 peer_allowas_in_set (struct peer *peer, afi_t afi, safi_t safi, int allow_num)
3541 {
3542   struct peer_group *group;
3543   struct listnode *node, *nnode;
3544
3545   if (allow_num < 1 || allow_num > 10)
3546     return BGP_ERR_INVALID_VALUE;
3547
3548   if (peer->allowas_in[afi][safi] != allow_num)
3549     {
3550       peer->allowas_in[afi][safi] = allow_num;
3551       SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ALLOWAS_IN);
3552       peer_change_action (peer, afi, safi, peer_change_reset_in);
3553     }
3554
3555   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3556     return 0;
3557
3558   group = peer->group;
3559   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3560     {
3561       if (peer->allowas_in[afi][safi] != allow_num)
3562         {
3563           peer->allowas_in[afi][safi] = allow_num;
3564           SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ALLOWAS_IN);
3565           peer_change_action (peer, afi, safi, peer_change_reset_in);
3566         }
3567           
3568     }
3569   return 0;
3570 }
3571
3572 int
3573 peer_allowas_in_unset (struct peer *peer, afi_t afi, safi_t safi)
3574 {
3575   struct peer_group *group;
3576   struct listnode *node, *nnode;
3577
3578   if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ALLOWAS_IN))
3579     {
3580       peer->allowas_in[afi][safi] = 0;
3581       peer_af_flag_unset (peer, afi, safi, PEER_FLAG_ALLOWAS_IN);
3582     }
3583
3584   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3585     return 0;
3586
3587   group = peer->group;
3588   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3589     {
3590       if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ALLOWAS_IN))
3591         {
3592           peer->allowas_in[afi][safi] = 0;
3593           peer_af_flag_unset (peer, afi, safi, PEER_FLAG_ALLOWAS_IN);
3594         }
3595     }
3596   return 0;
3597 }
3598
3599 int
3600 peer_local_as_set (struct peer *peer, as_t as, int no_prepend, int replace_as)
3601 {
3602   struct bgp *bgp = peer->bgp;
3603   struct peer_group *group;
3604   struct listnode *node, *nnode;
3605
3606   if (peer_sort (peer) != BGP_PEER_EBGP
3607       && peer_sort (peer) != BGP_PEER_INTERNAL)
3608     return BGP_ERR_LOCAL_AS_ALLOWED_ONLY_FOR_EBGP;
3609
3610   if (bgp->as == as)
3611     return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS;
3612
3613   if (peer_group_active (peer))
3614     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3615
3616   if (peer->as == as)
3617     return BGP_ERR_CANNOT_HAVE_LOCAL_AS_SAME_AS_REMOTE_AS;
3618
3619   if (peer->change_local_as == as &&
3620       ((CHECK_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND) && no_prepend)
3621        || (! CHECK_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND) && ! no_prepend)) &&
3622       ((CHECK_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS) && replace_as)
3623        || (! CHECK_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS) && ! replace_as)))
3624     return 0;
3625
3626   peer->change_local_as = as;
3627   if (no_prepend)
3628     SET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
3629   else
3630     UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
3631
3632   if (replace_as)
3633     SET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
3634   else
3635     UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
3636
3637   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3638     {
3639       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3640        {
3641          peer->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
3642          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3643                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3644        }
3645       else
3646         BGP_EVENT_ADD (peer, BGP_Stop);
3647
3648       return 0;
3649     }
3650
3651   group = peer->group;
3652   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3653     {
3654       peer->change_local_as = as;
3655       if (no_prepend)
3656         SET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
3657       else
3658         UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
3659
3660       if (replace_as)
3661         SET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
3662       else
3663         UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
3664
3665       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3666        {
3667          peer->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
3668          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3669                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3670        }
3671       else
3672         BGP_EVENT_ADD (peer, BGP_Stop);
3673     }
3674
3675   return 0;
3676 }
3677
3678 int
3679 peer_local_as_unset (struct peer *peer)
3680 {
3681   struct peer_group *group;
3682   struct listnode *node, *nnode;
3683
3684   if (peer_group_active (peer))
3685     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3686
3687   if (! peer->change_local_as)
3688     return 0;
3689
3690   peer->change_local_as = 0;
3691   UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
3692   UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
3693
3694   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3695     {
3696       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3697        {
3698          peer->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
3699          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3700                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3701        }
3702       else
3703         BGP_EVENT_ADD (peer, BGP_Stop);
3704
3705       return 0;
3706     }
3707
3708   group = peer->group;
3709   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3710     {
3711       peer->change_local_as = 0;
3712       UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND);
3713       UNSET_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS);
3714
3715       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3716        {
3717          peer->last_reset = PEER_DOWN_LOCAL_AS_CHANGE;
3718          bgp_notify_send (peer, BGP_NOTIFY_CEASE,
3719                           BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3720        }
3721       else
3722         BGP_EVENT_ADD (peer, BGP_Stop);
3723     }
3724   return 0;
3725 }
3726
3727 /* Set password for authenticating with the peer. */
3728 int
3729 peer_password_set (struct peer *peer, const char *password)
3730 {
3731   struct listnode *nn, *nnode;
3732   int len = password ? strlen(password) : 0;
3733   int ret = BGP_SUCCESS;
3734
3735   if ((len < PEER_PASSWORD_MINLEN) || (len > PEER_PASSWORD_MAXLEN))
3736     return BGP_ERR_INVALID_VALUE;
3737
3738   if (peer->password && strcmp (peer->password, password) == 0
3739       && ! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3740     return 0;
3741
3742   if (peer->password)
3743     XFREE (MTYPE_PEER_PASSWORD, peer->password);
3744   
3745   peer->password = XSTRDUP (MTYPE_PEER_PASSWORD, password);
3746
3747   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3748     {
3749       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3750         bgp_notify_send (peer, BGP_NOTIFY_CEASE, BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3751       else
3752         BGP_EVENT_ADD (peer, BGP_Stop);
3753         
3754       return (bgp_md5_set (peer) >= 0) ? BGP_SUCCESS : BGP_ERR_TCPSIG_FAILED;
3755     }
3756
3757   for (ALL_LIST_ELEMENTS (peer->group->peer, nn, nnode, peer))
3758     {
3759       if (peer->password && strcmp (peer->password, password) == 0)
3760         continue;
3761       
3762       if (peer->password)
3763         XFREE (MTYPE_PEER_PASSWORD, peer->password);
3764       
3765       peer->password = XSTRDUP(MTYPE_PEER_PASSWORD, password);
3766
3767       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3768         bgp_notify_send (peer, BGP_NOTIFY_CEASE, BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3769       else
3770         BGP_EVENT_ADD (peer, BGP_Stop);
3771       
3772       if (bgp_md5_set (peer) < 0)
3773         ret = BGP_ERR_TCPSIG_FAILED;
3774     }
3775
3776   return ret;
3777 }
3778
3779 int
3780 peer_password_unset (struct peer *peer)
3781 {
3782   struct listnode *nn, *nnode;
3783
3784   if (!peer->password
3785       && !CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3786     return 0;
3787
3788   if (!CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3789     {
3790       if (peer_group_active (peer)
3791           && peer->group->conf->password
3792           && strcmp (peer->group->conf->password, peer->password) == 0)
3793         return BGP_ERR_PEER_GROUP_HAS_THE_FLAG;
3794
3795       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3796         bgp_notify_send (peer, BGP_NOTIFY_CEASE, BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3797       else
3798         BGP_EVENT_ADD (peer, BGP_Stop);
3799
3800       if (peer->password)
3801         XFREE (MTYPE_PEER_PASSWORD, peer->password);
3802       
3803       peer->password = NULL;
3804       
3805       bgp_md5_set (peer);
3806
3807       return 0;
3808     }
3809
3810   XFREE (MTYPE_PEER_PASSWORD, peer->password);
3811   peer->password = NULL;
3812
3813   for (ALL_LIST_ELEMENTS (peer->group->peer, nn, nnode, peer))
3814     {
3815       if (!peer->password)
3816         continue;
3817
3818       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
3819         bgp_notify_send (peer, BGP_NOTIFY_CEASE, BGP_NOTIFY_CEASE_CONFIG_CHANGE);
3820       else
3821         BGP_EVENT_ADD (peer, BGP_Stop);
3822       
3823       XFREE (MTYPE_PEER_PASSWORD, peer->password);
3824       peer->password = NULL;
3825
3826       bgp_md5_set (peer);
3827     }
3828
3829   return 0;
3830 }
3831
3832 /* Set distribute list to the peer. */
3833 int
3834 peer_distribute_set (struct peer *peer, afi_t afi, safi_t safi, int direct, 
3835                      const char *name)
3836 {
3837   struct bgp_filter *filter;
3838   struct peer_group *group;
3839   struct listnode *node, *nnode;
3840
3841   if (! peer->afc[afi][safi])
3842     return BGP_ERR_PEER_INACTIVE;
3843
3844   if (direct != FILTER_IN && direct != FILTER_OUT)
3845     return BGP_ERR_INVALID_VALUE;
3846
3847   if (direct == FILTER_OUT && peer_is_group_member (peer, afi, safi))
3848     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3849
3850   filter = &peer->filter[afi][safi];
3851
3852   if (filter->plist[direct].name)
3853     return BGP_ERR_PEER_FILTER_CONFLICT;
3854
3855   if (filter->dlist[direct].name)
3856     free (filter->dlist[direct].name);
3857   filter->dlist[direct].name = strdup (name);
3858   filter->dlist[direct].alist = access_list_lookup (afi, name);
3859
3860   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3861     return 0;
3862
3863   group = peer->group;
3864   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3865     {
3866       filter = &peer->filter[afi][safi];
3867
3868       if (! peer->af_group[afi][safi])
3869         continue;
3870
3871       if (filter->dlist[direct].name)
3872         free (filter->dlist[direct].name);
3873       filter->dlist[direct].name = strdup (name);
3874       filter->dlist[direct].alist = access_list_lookup (afi, name);
3875     }
3876
3877   return 0;
3878 }
3879
3880 int
3881 peer_distribute_unset (struct peer *peer, afi_t afi, safi_t safi, int direct)
3882 {
3883   struct bgp_filter *filter;
3884   struct bgp_filter *gfilter;
3885   struct peer_group *group;
3886   struct listnode *node, *nnode;
3887
3888   if (! peer->afc[afi][safi])
3889     return BGP_ERR_PEER_INACTIVE;
3890
3891   if (direct != FILTER_IN && direct != FILTER_OUT)
3892     return BGP_ERR_INVALID_VALUE;
3893
3894   if (direct == FILTER_OUT && peer_is_group_member (peer, afi, safi))
3895     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
3896
3897   filter = &peer->filter[afi][safi];
3898
3899   /* apply peer-group filter */
3900   if (peer->af_group[afi][safi])
3901     {
3902       gfilter = &peer->group->conf->filter[afi][safi];
3903
3904       if (gfilter->dlist[direct].name)
3905         {
3906           if (filter->dlist[direct].name)
3907             free (filter->dlist[direct].name);
3908           filter->dlist[direct].name = strdup (gfilter->dlist[direct].name);
3909           filter->dlist[direct].alist = gfilter->dlist[direct].alist;
3910           return 0;
3911         }
3912     }
3913
3914   if (filter->dlist[direct].name)
3915     free (filter->dlist[direct].name);
3916   filter->dlist[direct].name = NULL;
3917   filter->dlist[direct].alist = NULL;
3918
3919   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
3920     return 0;
3921
3922   group = peer->group;
3923   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
3924     {
3925       filter = &peer->filter[afi][safi];
3926
3927       if (! peer->af_group[afi][safi])
3928         continue;
3929
3930       if (filter->dlist[direct].name)
3931         free (filter->dlist[direct].name);
3932       filter->dlist[direct].name = NULL;
3933       filter->dlist[direct].alist = NULL;
3934     }
3935
3936   return 0;
3937 }
3938
3939 /* Update distribute list. */
3940 static void
3941 peer_distribute_update (struct access_list *access)
3942 {
3943   afi_t afi;
3944   safi_t safi;
3945   int direct;
3946   struct listnode *mnode, *mnnode;
3947   struct listnode *node, *nnode;
3948   struct bgp *bgp;
3949   struct peer *peer;
3950   struct peer_group *group;
3951   struct bgp_filter *filter;
3952
3953   for (ALL_LIST_ELEMENTS (bm->bgp, mnode, mnnode, bgp))
3954     {
3955       for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
3956         {
3957           for (afi = AFI_IP; afi < AFI_MAX; afi++)
3958             for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
3959               {
3960                 filter = &peer->filter[afi][safi];
3961
3962                 for (direct = FILTER_IN; direct < FILTER_MAX; direct++)
3963                   {
3964                     if (filter->dlist[direct].name)
3965                       filter->dlist[direct].alist = 
3966                         access_list_lookup (afi, filter->dlist[direct].name);
3967                     else
3968                       filter->dlist[direct].alist = NULL;
3969                   }
3970               }
3971         }
3972       for (ALL_LIST_ELEMENTS (bgp->group, node, nnode, group))
3973         {
3974           for (afi = AFI_IP; afi < AFI_MAX; afi++)
3975             for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
3976               {
3977                 filter = &group->conf->filter[afi][safi];
3978
3979                 for (direct = FILTER_IN; direct < FILTER_MAX; direct++)
3980                   {
3981                     if (filter->dlist[direct].name)
3982                       filter->dlist[direct].alist = 
3983                         access_list_lookup (afi, filter->dlist[direct].name);
3984                     else
3985                       filter->dlist[direct].alist = NULL;
3986                   }
3987               }
3988         }
3989     }
3990 }
3991
3992 /* Set prefix list to the peer. */
3993 int
3994 peer_prefix_list_set (struct peer *peer, afi_t afi, safi_t safi, int direct, 
3995                       const char *name)
3996 {
3997   struct bgp_filter *filter;
3998   struct peer_group *group;
3999   struct listnode *node, *nnode;
4000
4001   if (! peer->afc[afi][safi])
4002     return BGP_ERR_PEER_INACTIVE;
4003
4004   if (direct != FILTER_IN && direct != FILTER_OUT)
4005     return BGP_ERR_INVALID_VALUE;
4006
4007   if (direct == FILTER_OUT && peer_is_group_member (peer, afi, safi))
4008     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4009
4010   filter = &peer->filter[afi][safi];
4011
4012   if (filter->dlist[direct].name)
4013     return BGP_ERR_PEER_FILTER_CONFLICT;
4014
4015   if (filter->plist[direct].name)
4016     free (filter->plist[direct].name);
4017   filter->plist[direct].name = strdup (name);
4018   filter->plist[direct].plist = prefix_list_lookup (afi, name);
4019
4020   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4021     return 0;
4022
4023   group = peer->group;
4024   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4025     {
4026       filter = &peer->filter[afi][safi];
4027
4028       if (! peer->af_group[afi][safi])
4029         continue;
4030
4031       if (filter->plist[direct].name)
4032         free (filter->plist[direct].name);
4033       filter->plist[direct].name = strdup (name);
4034       filter->plist[direct].plist = prefix_list_lookup (afi, name);
4035     }
4036   return 0;
4037 }
4038
4039 int
4040 peer_prefix_list_unset (struct peer *peer, afi_t afi, safi_t safi, int direct)
4041 {
4042   struct bgp_filter *filter;
4043   struct bgp_filter *gfilter;
4044   struct peer_group *group;
4045   struct listnode *node, *nnode;
4046
4047   if (! peer->afc[afi][safi])
4048     return BGP_ERR_PEER_INACTIVE;
4049
4050   if (direct != FILTER_IN && direct != FILTER_OUT)
4051     return BGP_ERR_INVALID_VALUE;
4052
4053   if (direct == FILTER_OUT && peer_is_group_member (peer, afi, safi))
4054     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4055
4056   filter = &peer->filter[afi][safi];
4057
4058   /* apply peer-group filter */
4059   if (peer->af_group[afi][safi])
4060     {
4061       gfilter = &peer->group->conf->filter[afi][safi];
4062
4063       if (gfilter->plist[direct].name)
4064         {
4065           if (filter->plist[direct].name)
4066             free (filter->plist[direct].name);
4067           filter->plist[direct].name = strdup (gfilter->plist[direct].name);
4068           filter->plist[direct].plist = gfilter->plist[direct].plist;
4069           return 0;
4070         }
4071     }
4072
4073   if (filter->plist[direct].name)
4074     free (filter->plist[direct].name);
4075   filter->plist[direct].name = NULL;
4076   filter->plist[direct].plist = NULL;
4077
4078   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4079     return 0;
4080
4081   group = peer->group;
4082   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4083     {
4084       filter = &peer->filter[afi][safi];
4085
4086       if (! peer->af_group[afi][safi])
4087         continue;
4088
4089       if (filter->plist[direct].name)
4090         free (filter->plist[direct].name);
4091       filter->plist[direct].name = NULL;
4092       filter->plist[direct].plist = NULL;
4093     }
4094
4095   return 0;
4096 }
4097
4098 /* Update prefix-list list. */
4099 static void
4100 peer_prefix_list_update (struct prefix_list *plist)
4101 {
4102   struct listnode *mnode, *mnnode;
4103   struct listnode *node, *nnode;
4104   struct bgp *bgp;
4105   struct peer *peer;
4106   struct peer_group *group;
4107   struct bgp_filter *filter;
4108   afi_t afi;
4109   safi_t safi;
4110   int direct;
4111
4112   for (ALL_LIST_ELEMENTS (bm->bgp, mnode, mnnode, bgp))
4113     {
4114       for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
4115         {
4116           for (afi = AFI_IP; afi < AFI_MAX; afi++)
4117             for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
4118               {
4119                 filter = &peer->filter[afi][safi];
4120
4121                 for (direct = FILTER_IN; direct < FILTER_MAX; direct++)
4122                   {
4123                     if (filter->plist[direct].name)
4124                       filter->plist[direct].plist = 
4125                         prefix_list_lookup (afi, filter->plist[direct].name);
4126                     else
4127                       filter->plist[direct].plist = NULL;
4128                   }
4129               }
4130         }
4131       for (ALL_LIST_ELEMENTS (bgp->group, node, nnode, group))
4132         {
4133           for (afi = AFI_IP; afi < AFI_MAX; afi++)
4134             for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
4135               {
4136                 filter = &group->conf->filter[afi][safi];
4137
4138                 for (direct = FILTER_IN; direct < FILTER_MAX; direct++)
4139                   {
4140                     if (filter->plist[direct].name)
4141                       filter->plist[direct].plist = 
4142                         prefix_list_lookup (afi, filter->plist[direct].name);
4143                     else
4144                       filter->plist[direct].plist = NULL;
4145                   }
4146               }
4147         }
4148     }
4149 }
4150
4151 int
4152 peer_aslist_set (struct peer *peer, afi_t afi, safi_t safi, int direct,
4153                  const char *name)
4154 {
4155   struct bgp_filter *filter;
4156   struct peer_group *group;
4157   struct listnode *node, *nnode;
4158
4159   if (! peer->afc[afi][safi])
4160     return BGP_ERR_PEER_INACTIVE;
4161
4162   if (direct != FILTER_IN && direct != FILTER_OUT)
4163     return BGP_ERR_INVALID_VALUE;
4164
4165   if (direct == FILTER_OUT && peer_is_group_member (peer, afi, safi))
4166     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4167
4168   filter = &peer->filter[afi][safi];
4169
4170   if (filter->aslist[direct].name)
4171     free (filter->aslist[direct].name);
4172   filter->aslist[direct].name = strdup (name);
4173   filter->aslist[direct].aslist = as_list_lookup (name);
4174
4175   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4176     return 0;
4177
4178   group = peer->group;
4179   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4180     {
4181       filter = &peer->filter[afi][safi];
4182
4183       if (! peer->af_group[afi][safi])
4184         continue;
4185
4186       if (filter->aslist[direct].name)
4187         free (filter->aslist[direct].name);
4188       filter->aslist[direct].name = strdup (name);
4189       filter->aslist[direct].aslist = as_list_lookup (name);
4190     }
4191   return 0;
4192 }
4193
4194 int
4195 peer_aslist_unset (struct peer *peer,afi_t afi, safi_t safi, int direct)
4196 {
4197   struct bgp_filter *filter;
4198   struct bgp_filter *gfilter;
4199   struct peer_group *group;
4200   struct listnode *node, *nnode;
4201
4202   if (! peer->afc[afi][safi])
4203     return BGP_ERR_PEER_INACTIVE;
4204
4205   if (direct != FILTER_IN && direct != FILTER_OUT)
4206     return BGP_ERR_INVALID_VALUE;
4207
4208   if (direct == FILTER_OUT && peer_is_group_member (peer, afi, safi))
4209     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4210
4211   filter = &peer->filter[afi][safi];
4212
4213   /* apply peer-group filter */
4214   if (peer->af_group[afi][safi])
4215     {
4216       gfilter = &peer->group->conf->filter[afi][safi];
4217
4218       if (gfilter->aslist[direct].name)
4219         {
4220           if (filter->aslist[direct].name)
4221             free (filter->aslist[direct].name);
4222           filter->aslist[direct].name = strdup (gfilter->aslist[direct].name);
4223           filter->aslist[direct].aslist = gfilter->aslist[direct].aslist;
4224           return 0;
4225         }
4226     }
4227
4228   if (filter->aslist[direct].name)
4229     free (filter->aslist[direct].name);
4230   filter->aslist[direct].name = NULL;
4231   filter->aslist[direct].aslist = NULL;
4232
4233   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4234     return 0;
4235
4236   group = peer->group;
4237   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4238     {
4239       filter = &peer->filter[afi][safi];
4240
4241       if (! peer->af_group[afi][safi])
4242         continue;
4243
4244       if (filter->aslist[direct].name)
4245         free (filter->aslist[direct].name);
4246       filter->aslist[direct].name = NULL;
4247       filter->aslist[direct].aslist = NULL;
4248     }
4249
4250   return 0;
4251 }
4252
4253 static void
4254 peer_aslist_update (void)
4255 {
4256   afi_t afi;
4257   safi_t safi;
4258   int direct;
4259   struct listnode *mnode, *mnnode;
4260   struct listnode *node, *nnode;
4261   struct bgp *bgp;
4262   struct peer *peer;
4263   struct peer_group *group;
4264   struct bgp_filter *filter;
4265
4266   for (ALL_LIST_ELEMENTS (bm->bgp, mnode, mnnode, bgp))
4267     {
4268       for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
4269         {
4270           for (afi = AFI_IP; afi < AFI_MAX; afi++)
4271             for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
4272               {
4273                 filter = &peer->filter[afi][safi];
4274
4275                 for (direct = FILTER_IN; direct < FILTER_MAX; direct++)
4276                   {
4277                     if (filter->aslist[direct].name)
4278                       filter->aslist[direct].aslist = 
4279                         as_list_lookup (filter->aslist[direct].name);
4280                     else
4281                       filter->aslist[direct].aslist = NULL;
4282                   }
4283               }
4284         }
4285       for (ALL_LIST_ELEMENTS (bgp->group, node, nnode, group))
4286         {
4287           for (afi = AFI_IP; afi < AFI_MAX; afi++)
4288             for (safi = SAFI_UNICAST; safi < SAFI_MAX; safi++)
4289               {
4290                 filter = &group->conf->filter[afi][safi];
4291
4292                 for (direct = FILTER_IN; direct < FILTER_MAX; direct++)
4293                   {
4294                     if (filter->aslist[direct].name)
4295                       filter->aslist[direct].aslist = 
4296                         as_list_lookup (filter->aslist[direct].name);
4297                     else
4298                       filter->aslist[direct].aslist = NULL;
4299                   }
4300               }
4301         }
4302     }
4303 }
4304
4305 /* Set route-map to the peer. */
4306 int
4307 peer_route_map_set (struct peer *peer, afi_t afi, safi_t safi, int direct, 
4308                     const char *name)
4309 {
4310   struct bgp_filter *filter;
4311   struct peer_group *group;
4312   struct listnode *node, *nnode;
4313
4314   if (! peer->afc[afi][safi])
4315     return BGP_ERR_PEER_INACTIVE;
4316
4317   if (direct != RMAP_IN && direct != RMAP_OUT &&
4318       direct != RMAP_IMPORT && direct != RMAP_EXPORT)
4319     return BGP_ERR_INVALID_VALUE;
4320
4321   if ( (direct == RMAP_OUT || direct == RMAP_IMPORT)
4322       && peer_is_group_member (peer, afi, safi))
4323     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4324
4325   filter = &peer->filter[afi][safi];
4326
4327   if (filter->map[direct].name)
4328     free (filter->map[direct].name);
4329   
4330   filter->map[direct].name = strdup (name);
4331   filter->map[direct].map = route_map_lookup_by_name (name);
4332
4333   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4334     return 0;
4335
4336   group = peer->group;
4337   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4338     {
4339       filter = &peer->filter[afi][safi];
4340
4341       if (! peer->af_group[afi][safi])
4342         continue;
4343
4344       if (filter->map[direct].name)
4345         free (filter->map[direct].name);
4346       filter->map[direct].name = strdup (name);
4347       filter->map[direct].map = route_map_lookup_by_name (name);
4348     }
4349   return 0;
4350 }
4351
4352 /* Unset route-map from the peer. */
4353 int
4354 peer_route_map_unset (struct peer *peer, afi_t afi, safi_t safi, int direct)
4355 {
4356   struct bgp_filter *filter;
4357   struct bgp_filter *gfilter;
4358   struct peer_group *group;
4359   struct listnode *node, *nnode;
4360
4361   if (! peer->afc[afi][safi])
4362     return BGP_ERR_PEER_INACTIVE;
4363
4364   if (direct != RMAP_IN && direct != RMAP_OUT &&
4365       direct != RMAP_IMPORT && direct != RMAP_EXPORT)
4366     return BGP_ERR_INVALID_VALUE;
4367
4368   if ( (direct == RMAP_OUT || direct == RMAP_IMPORT)
4369       && peer_is_group_member (peer, afi, safi))
4370     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4371
4372   filter = &peer->filter[afi][safi];
4373
4374   /* apply peer-group filter */
4375   if (peer->af_group[afi][safi])
4376     {
4377       gfilter = &peer->group->conf->filter[afi][safi];
4378
4379       if (gfilter->map[direct].name)
4380         {
4381           if (filter->map[direct].name)
4382             free (filter->map[direct].name);
4383           filter->map[direct].name = strdup (gfilter->map[direct].name);
4384           filter->map[direct].map = gfilter->map[direct].map;
4385           return 0;
4386         }
4387     }
4388
4389   if (filter->map[direct].name)
4390     free (filter->map[direct].name);
4391   filter->map[direct].name = NULL;
4392   filter->map[direct].map = NULL;
4393
4394   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4395     return 0;
4396
4397   group = peer->group;
4398   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4399     {
4400       filter = &peer->filter[afi][safi];
4401
4402       if (! peer->af_group[afi][safi])
4403         continue;
4404
4405       if (filter->map[direct].name)
4406         free (filter->map[direct].name);
4407       filter->map[direct].name = NULL;
4408       filter->map[direct].map = NULL;
4409     }
4410   return 0;
4411 }
4412
4413 /* Set unsuppress-map to the peer. */
4414 int
4415 peer_unsuppress_map_set (struct peer *peer, afi_t afi, safi_t safi, 
4416                          const char *name)
4417 {
4418   struct bgp_filter *filter;
4419   struct peer_group *group;
4420   struct listnode *node, *nnode;
4421
4422   if (! peer->afc[afi][safi])
4423     return BGP_ERR_PEER_INACTIVE;
4424
4425   if (peer_is_group_member (peer, afi, safi))
4426     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4427       
4428   filter = &peer->filter[afi][safi];
4429
4430   if (filter->usmap.name)
4431     free (filter->usmap.name);
4432   
4433   filter->usmap.name = strdup (name);
4434   filter->usmap.map = route_map_lookup_by_name (name);
4435
4436   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4437     return 0;
4438
4439   group = peer->group;
4440   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4441     {
4442       filter = &peer->filter[afi][safi];
4443
4444       if (! peer->af_group[afi][safi])
4445         continue;
4446
4447       if (filter->usmap.name)
4448         free (filter->usmap.name);
4449       filter->usmap.name = strdup (name);
4450       filter->usmap.map = route_map_lookup_by_name (name);
4451     }
4452   return 0;
4453 }
4454
4455 /* Unset route-map from the peer. */
4456 int
4457 peer_unsuppress_map_unset (struct peer *peer, afi_t afi, safi_t safi)
4458 {
4459   struct bgp_filter *filter;
4460   struct peer_group *group;
4461   struct listnode *node, *nnode;
4462
4463   if (! peer->afc[afi][safi])
4464     return BGP_ERR_PEER_INACTIVE;
4465   
4466   if (peer_is_group_member (peer, afi, safi))
4467     return BGP_ERR_INVALID_FOR_PEER_GROUP_MEMBER;
4468
4469   filter = &peer->filter[afi][safi];
4470
4471   if (filter->usmap.name)
4472     free (filter->usmap.name);
4473   filter->usmap.name = NULL;
4474   filter->usmap.map = NULL;
4475
4476   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4477     return 0;
4478
4479   group = peer->group;
4480   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4481     {
4482       filter = &peer->filter[afi][safi];
4483
4484       if (! peer->af_group[afi][safi])
4485         continue;
4486
4487       if (filter->usmap.name)
4488         free (filter->usmap.name);
4489       filter->usmap.name = NULL;
4490       filter->usmap.map = NULL;
4491     }
4492   return 0;
4493 }
4494
4495 int
4496 peer_maximum_prefix_set (struct peer *peer, afi_t afi, safi_t safi,
4497                          u_int32_t max, u_char threshold,
4498                          int warning, u_int16_t restart)
4499 {
4500   struct peer_group *group;
4501   struct listnode *node, *nnode;
4502
4503   if (! peer->afc[afi][safi])
4504     return BGP_ERR_PEER_INACTIVE;
4505
4506   SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX);
4507   peer->pmax[afi][safi] = max;
4508   peer->pmax_threshold[afi][safi] = threshold;
4509   peer->pmax_restart[afi][safi] = restart;
4510   if (warning)
4511     SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4512   else
4513     UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4514
4515   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4516     {
4517       group = peer->group;
4518       for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4519         {
4520           if (! peer->af_group[afi][safi])
4521             continue;
4522
4523           SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX);
4524           peer->pmax[afi][safi] = max;
4525           peer->pmax_threshold[afi][safi] = threshold;
4526           peer->pmax_restart[afi][safi] = restart;
4527           if (warning)
4528             SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4529           else
4530             UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4531
4532           if ((peer->status == Established) && (peer->afc[afi][safi]))
4533             bgp_maximum_prefix_overflow (peer, afi, safi, 1);
4534         }
4535     }
4536   else
4537     {
4538       if ((peer->status == Established) && (peer->afc[afi][safi]))
4539         bgp_maximum_prefix_overflow (peer, afi, safi, 1);
4540     }
4541
4542   return 0;
4543 }
4544
4545 int
4546 peer_maximum_prefix_unset (struct peer *peer, afi_t afi, safi_t safi)
4547 {
4548   struct peer_group *group;
4549   struct listnode *node, *nnode;
4550
4551   if (! peer->afc[afi][safi])
4552     return BGP_ERR_PEER_INACTIVE;
4553
4554   /* apply peer-group config */
4555   if (peer->af_group[afi][safi])
4556     {
4557       if (CHECK_FLAG (peer->group->conf->af_flags[afi][safi],
4558           PEER_FLAG_MAX_PREFIX))
4559         SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX);
4560       else
4561         UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX);
4562
4563       if (CHECK_FLAG (peer->group->conf->af_flags[afi][safi],
4564           PEER_FLAG_MAX_PREFIX_WARNING))
4565         SET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4566       else
4567         UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4568
4569       peer->pmax[afi][safi] = peer->group->conf->pmax[afi][safi];
4570       peer->pmax_threshold[afi][safi] = peer->group->conf->pmax_threshold[afi][safi];
4571       peer->pmax_restart[afi][safi] = peer->group->conf->pmax_restart[afi][safi];
4572       return 0;
4573     }
4574
4575   UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX);
4576   UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4577   peer->pmax[afi][safi] = 0;
4578   peer->pmax_threshold[afi][safi] = 0;
4579   peer->pmax_restart[afi][safi] = 0;
4580
4581   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4582     return 0;
4583
4584   group = peer->group;
4585   for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4586     {
4587       if (! peer->af_group[afi][safi])
4588         continue;
4589
4590       UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX);
4591       UNSET_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING);
4592       peer->pmax[afi][safi] = 0;
4593       peer->pmax_threshold[afi][safi] = 0;
4594       peer->pmax_restart[afi][safi] = 0;
4595     }
4596   return 0;
4597 }
4598
4599 /* Set # of hops between us and BGP peer. */
4600 int
4601 peer_ttl_security_hops_set (struct peer *peer, int gtsm_hops)
4602 {
4603   struct peer_group *group;
4604   struct listnode *node, *nnode;
4605   struct peer *peer1;
4606
4607   zlog_debug ("peer_ttl_security_hops_set: set gtsm_hops to %d for %s", gtsm_hops, peer->host);
4608
4609   if (peer->ttl != 0)
4610     return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
4611
4612   if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4613     {
4614       group = peer->group;
4615       for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer1))
4616         {
4617           if (peer1->ttl != 0)
4618             return BGP_ERR_NO_EBGP_MULTIHOP_WITH_TTLHACK;
4619         }
4620     }
4621
4622   peer->gtsm_hops = gtsm_hops;
4623
4624   if (! CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4625     {
4626       bgp_set_socket_ttl (peer, peer->fd);
4627     }
4628   else
4629     {
4630       group = peer->group;
4631       for (ALL_LIST_ELEMENTS (group->peer, node, nnode, peer))
4632         {
4633           peer->gtsm_hops = gtsm_hops;
4634
4635           /* Change setting of existing peer
4636            *   established then change value (may break connectivity)
4637            *   not established yet (teardown session and restart)
4638            *   no session then do nothing (will get handled by next connection)
4639            */
4640           if (peer->status == Established)
4641             {
4642               bgp_set_socket_ttl (peer, peer->fd);
4643             }
4644           else if (peer->status < Established)
4645             {
4646               if (BGP_DEBUG (events, EVENTS))
4647                 zlog_debug ("%s Min-ttl changed", peer->host);
4648               BGP_EVENT_ADD (peer, BGP_Stop);
4649             }
4650         }
4651     }
4652
4653   return 0;
4654 }
4655
4656 int
4657 peer_clear (struct peer *peer)
4658 {
4659   if (! CHECK_FLAG (peer->flags, PEER_FLAG_SHUTDOWN))
4660     {
4661       if (CHECK_FLAG (peer->sflags, PEER_STATUS_PREFIX_OVERFLOW))
4662         {
4663           UNSET_FLAG (peer->sflags, PEER_STATUS_PREFIX_OVERFLOW);
4664           if (peer->t_pmax_restart)
4665             {
4666               BGP_TIMER_OFF (peer->t_pmax_restart);
4667               if (BGP_DEBUG (events, EVENTS))
4668                 zlog_debug ("%s Maximum-prefix restart timer canceled",
4669                             peer->host);
4670             }
4671           BGP_EVENT_ADD (peer, BGP_Start);
4672           return 0;
4673         }
4674
4675       peer->v_start = BGP_INIT_START_TIMER;
4676       if (BGP_IS_VALID_STATE_FOR_NOTIF(peer->status))
4677         bgp_notify_send (peer, BGP_NOTIFY_CEASE,
4678                          BGP_NOTIFY_CEASE_ADMIN_RESET);
4679       else
4680         BGP_EVENT_ADD (peer, BGP_Stop);
4681     }
4682   return 0;
4683 }
4684
4685 int
4686 peer_clear_soft (struct peer *peer, afi_t afi, safi_t safi,
4687                  enum bgp_clear_type stype)
4688 {
4689   if (peer->status != Established)
4690     return 0;
4691
4692   if (! peer->afc[afi][safi])
4693     return BGP_ERR_AF_UNCONFIGURED;
4694
4695   peer->rtt = sockopt_tcp_rtt (peer->fd);
4696
4697   if (stype == BGP_CLEAR_SOFT_RSCLIENT)
4698     {
4699       if (! CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT))
4700         return 0;
4701       bgp_check_local_routes_rsclient (peer, afi, safi);
4702       bgp_soft_reconfig_rsclient (peer, afi, safi);
4703     }
4704
4705   if (stype == BGP_CLEAR_SOFT_OUT || stype == BGP_CLEAR_SOFT_BOTH)
4706     bgp_announce_route (peer, afi, safi);
4707
4708   if (stype == BGP_CLEAR_SOFT_IN_ORF_PREFIX)
4709     {
4710       if (CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ORF_PREFIX_SM_ADV)
4711           && (CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ORF_PREFIX_RM_RCV)
4712               || CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ORF_PREFIX_RM_OLD_RCV)))
4713         {
4714           struct bgp_filter *filter = &peer->filter[afi][safi];
4715           u_char prefix_type;
4716
4717           if (CHECK_FLAG (peer->af_cap[afi][safi], PEER_CAP_ORF_PREFIX_RM_RCV))
4718             prefix_type = ORF_TYPE_PREFIX;
4719           else
4720             prefix_type = ORF_TYPE_PREFIX_OLD;
4721
4722           if (filter->plist[FILTER_IN].plist)
4723             {
4724               if (CHECK_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_ORF_PREFIX_SEND))
4725                 bgp_route_refresh_send (peer, afi, safi,
4726                                         prefix_type, REFRESH_DEFER, 1);
4727               bgp_route_refresh_send (peer, afi, safi, prefix_type,
4728                                       REFRESH_IMMEDIATE, 0);
4729             }
4730           else
4731             {
4732               if (CHECK_FLAG (peer->af_sflags[afi][safi], PEER_STATUS_ORF_PREFIX_SEND))
4733                 bgp_route_refresh_send (peer, afi, safi,
4734                                         prefix_type, REFRESH_IMMEDIATE, 1);
4735               else
4736                 bgp_route_refresh_send (peer, afi, safi, 0, 0, 0);
4737             }
4738           return 0;
4739         }
4740     }
4741
4742   if (stype == BGP_CLEAR_SOFT_IN || stype == BGP_CLEAR_SOFT_BOTH
4743       || stype == BGP_CLEAR_SOFT_IN_ORF_PREFIX)
4744     {
4745       /* If neighbor has soft reconfiguration inbound flag.
4746          Use Adj-RIB-In database. */
4747       if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SOFT_RECONFIG))
4748         bgp_soft_reconfig_in (peer, afi, safi);
4749       else
4750         {
4751           /* If neighbor has route refresh capability, send route refresh
4752              message to the peer. */
4753           if (CHECK_FLAG (peer->cap, PEER_CAP_REFRESH_OLD_RCV)
4754               || CHECK_FLAG (peer->cap, PEER_CAP_REFRESH_NEW_RCV))
4755             bgp_route_refresh_send (peer, afi, safi, 0, 0, 0);
4756           else
4757             return BGP_ERR_SOFT_RECONFIG_UNCONFIGURED;
4758         }
4759     }
4760   return 0;
4761 }
4762
4763 /* Display peer uptime.*/
4764 /* XXX: why does this function return char * when it takes buffer? */
4765 char *
4766 peer_uptime (time_t uptime2, char *buf, size_t len)
4767 {
4768   time_t uptime1;
4769   struct tm *tm;
4770
4771   /* Check buffer length. */
4772   if (len < BGP_UPTIME_LEN)
4773     {
4774       zlog_warn ("peer_uptime (): buffer shortage %lu", (u_long)len);
4775       /* XXX: should return status instead of buf... */
4776       snprintf (buf, len, "<error> "); 
4777       return buf;
4778     }
4779
4780   /* If there is no connection has been done before print `never'. */
4781   if (uptime2 == 0)
4782     {
4783       snprintf (buf, len, "never   ");
4784       return buf;
4785     }
4786
4787   /* Get current time. */
4788   uptime1 = bgp_clock ();
4789   uptime1 -= uptime2;
4790   tm = gmtime (&uptime1);
4791   
4792   /* Making formatted timer strings. */
4793 #define ONE_DAY_SECOND 60*60*24
4794 #define ONE_WEEK_SECOND ONE_DAY_SECOND*7
4795 #define ONE_YEAR_SECOND ONE_DAY_SECOND*365
4796
4797   if (uptime1 < ONE_DAY_SECOND)
4798     snprintf (buf, len, "%02d:%02d:%02d", 
4799               tm->tm_hour, tm->tm_min, tm->tm_sec);
4800   else if (uptime1 < ONE_WEEK_SECOND)
4801     snprintf (buf, len, "%dd%02dh%02dm", 
4802               tm->tm_yday, tm->tm_hour, tm->tm_min);
4803   else if (uptime1 < ONE_YEAR_SECOND)
4804     snprintf (buf, len, "%02dw%dd%02dh", 
4805               tm->tm_yday/7, tm->tm_yday - ((tm->tm_yday/7) * 7), tm->tm_hour);
4806   else
4807     snprintf (buf, len, "%02dy%02dw%dd", 
4808               tm->tm_year - 70, tm->tm_yday/7, 
4809               tm->tm_yday - ((tm->tm_yday/7) * 7));
4810   return buf;
4811 }
4812
4813 static void
4814 bgp_config_write_filter (struct vty *vty, struct peer *peer,
4815                          afi_t afi, safi_t safi)
4816 {
4817   struct bgp_filter *filter;
4818   struct bgp_filter *gfilter = NULL;
4819   char *addr;
4820   int in = FILTER_IN;
4821   int out = FILTER_OUT;
4822
4823   addr = peer->host;
4824   filter = &peer->filter[afi][safi];
4825   if (peer->af_group[afi][safi])
4826     gfilter = &peer->group->conf->filter[afi][safi];
4827
4828   /* distribute-list. */
4829   if (filter->dlist[in].name)
4830     if (! gfilter || ! gfilter->dlist[in].name
4831         || strcmp (filter->dlist[in].name, gfilter->dlist[in].name) != 0)
4832     vty_out (vty, " neighbor %s distribute-list %s in%s", addr, 
4833              filter->dlist[in].name, VTY_NEWLINE);
4834   if (filter->dlist[out].name && ! gfilter)
4835     vty_out (vty, " neighbor %s distribute-list %s out%s", addr, 
4836              filter->dlist[out].name, VTY_NEWLINE);
4837
4838   /* prefix-list. */
4839   if (filter->plist[in].name)
4840     if (! gfilter || ! gfilter->plist[in].name
4841         || strcmp (filter->plist[in].name, gfilter->plist[in].name) != 0)
4842     vty_out (vty, " neighbor %s prefix-list %s in%s", addr, 
4843              filter->plist[in].name, VTY_NEWLINE);
4844   if (filter->plist[out].name && ! gfilter)
4845     vty_out (vty, " neighbor %s prefix-list %s out%s", addr, 
4846              filter->plist[out].name, VTY_NEWLINE);
4847
4848   /* route-map. */
4849   if (filter->map[RMAP_IN].name)
4850     if (! gfilter || ! gfilter->map[RMAP_IN].name
4851        || strcmp (filter->map[RMAP_IN].name, gfilter->map[RMAP_IN].name) != 0)
4852       vty_out (vty, " neighbor %s route-map %s in%s", addr, 
4853               filter->map[RMAP_IN].name, VTY_NEWLINE);
4854   if (filter->map[RMAP_OUT].name && ! gfilter)
4855     vty_out (vty, " neighbor %s route-map %s out%s", addr, 
4856             filter->map[RMAP_OUT].name, VTY_NEWLINE);
4857   if (filter->map[RMAP_IMPORT].name && ! gfilter)
4858     vty_out (vty, " neighbor %s route-map %s import%s", addr,
4859         filter->map[RMAP_IMPORT].name, VTY_NEWLINE);
4860   if (filter->map[RMAP_EXPORT].name)
4861     if (! gfilter || ! gfilter->map[RMAP_EXPORT].name
4862     || strcmp (filter->map[RMAP_EXPORT].name,
4863                     gfilter->map[RMAP_EXPORT].name) != 0)
4864     vty_out (vty, " neighbor %s route-map %s export%s", addr,
4865         filter->map[RMAP_EXPORT].name, VTY_NEWLINE);
4866
4867   /* unsuppress-map */
4868   if (filter->usmap.name && ! gfilter)
4869     vty_out (vty, " neighbor %s unsuppress-map %s%s", addr,
4870              filter->usmap.name, VTY_NEWLINE);
4871
4872   /* filter-list. */
4873   if (filter->aslist[in].name)
4874     if (! gfilter || ! gfilter->aslist[in].name
4875         || strcmp (filter->aslist[in].name, gfilter->aslist[in].name) != 0)
4876       vty_out (vty, " neighbor %s filter-list %s in%s", addr, 
4877                filter->aslist[in].name, VTY_NEWLINE);
4878   if (filter->aslist[out].name && ! gfilter)
4879     vty_out (vty, " neighbor %s filter-list %s out%s", addr, 
4880              filter->aslist[out].name, VTY_NEWLINE);
4881 }
4882
4883 /* BGP peer configuration display function. */
4884 static void
4885 bgp_config_write_peer (struct vty *vty, struct bgp *bgp,
4886                        struct peer *peer, afi_t afi, safi_t safi)
4887 {
4888   struct peer *g_peer = NULL;
4889   char buf[SU_ADDRSTRLEN];
4890   char *addr;
4891
4892   addr = peer->host;
4893   if (peer_group_active (peer))
4894     g_peer = peer->group->conf;
4895
4896   /************************************
4897    ****** Global to the neighbor ******
4898    ************************************/
4899   if (afi == AFI_IP && safi == SAFI_UNICAST)
4900     {
4901       /* remote-as. */
4902       if (! peer_group_active (peer))
4903         {
4904           if (CHECK_FLAG (peer->sflags, PEER_STATUS_GROUP))
4905             vty_out (vty, " neighbor %s peer-group%s", addr,
4906                      VTY_NEWLINE);
4907           if (peer->as)
4908             vty_out (vty, " neighbor %s remote-as %u%s", addr, peer->as,
4909                      VTY_NEWLINE);
4910         }
4911       else
4912         {
4913           if (! g_peer->as)
4914             vty_out (vty, " neighbor %s remote-as %u%s", addr, peer->as,
4915                      VTY_NEWLINE);
4916           if (peer->af_group[AFI_IP][SAFI_UNICAST])
4917             vty_out (vty, " neighbor %s peer-group %s%s", addr,
4918                      peer->group->name, VTY_NEWLINE);
4919         }
4920
4921       /* local-as. */
4922       if (peer->change_local_as)
4923         if (! peer_group_active (peer))
4924           vty_out (vty, " neighbor %s local-as %u%s%s%s", addr,
4925                    peer->change_local_as,
4926                    CHECK_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_NO_PREPEND) ?
4927                    " no-prepend" : "",
4928                    CHECK_FLAG (peer->flags, PEER_FLAG_LOCAL_AS_REPLACE_AS) ?
4929                    " replace-as" : "", VTY_NEWLINE);
4930
4931       /* Description. */
4932       if (peer->desc)
4933         vty_out (vty, " neighbor %s description %s%s", addr, peer->desc,
4934                  VTY_NEWLINE);
4935
4936       /* Shutdown. */
4937       if (CHECK_FLAG (peer->flags, PEER_FLAG_SHUTDOWN))
4938         if (! peer_group_active (peer) ||
4939             ! CHECK_FLAG (g_peer->flags, PEER_FLAG_SHUTDOWN))
4940           vty_out (vty, " neighbor %s shutdown%s", addr, VTY_NEWLINE);
4941
4942       /* Password. */
4943       if (peer->password)
4944         if (!peer_group_active (peer)
4945             || ! g_peer->password
4946             || strcmp (peer->password, g_peer->password) != 0)
4947           vty_out (vty, " neighbor %s password %s%s", addr, peer->password,
4948                    VTY_NEWLINE);
4949
4950       /* BGP port. */
4951       if (peer->port != BGP_PORT_DEFAULT)
4952         vty_out (vty, " neighbor %s port %d%s", addr, peer->port,
4953                  VTY_NEWLINE);
4954
4955       /* Local interface name. */
4956       if (peer->ifname)
4957         vty_out (vty, " neighbor %s interface %s%s", addr, peer->ifname,
4958                  VTY_NEWLINE);
4959   
4960       /* Passive. */
4961       if (CHECK_FLAG (peer->flags, PEER_FLAG_PASSIVE))
4962         if (! peer_group_active (peer) ||
4963             ! CHECK_FLAG (g_peer->flags, PEER_FLAG_PASSIVE))
4964           vty_out (vty, " neighbor %s passive%s", addr, VTY_NEWLINE);
4965
4966       /* TTL option */
4967       if (peer->gtsm_hops && ! peer_group_active (peer))
4968         vty_out (vty, " neighbor %s ttl-security hops %d%s", addr,
4969                  peer->gtsm_hops, VTY_NEWLINE);
4970       else if (peer->ttl && ! peer_group_active (peer))
4971         vty_out (vty, " neighbor %s ebgp-multihop %d%s", addr, peer->ttl,
4972                  VTY_NEWLINE);
4973
4974       /* disable-connected-check.  */
4975       if (CHECK_FLAG (peer->flags, PEER_FLAG_DISABLE_CONNECTED_CHECK))
4976         if (! peer_group_active (peer) ||
4977             ! CHECK_FLAG (g_peer->flags, PEER_FLAG_DISABLE_CONNECTED_CHECK))
4978           vty_out (vty, " neighbor %s disable-connected-check%s", addr, VTY_NEWLINE);
4979
4980       /* Update-source. */
4981       if (peer->update_if)
4982         if (! peer_group_active (peer) || ! g_peer->update_if
4983             || strcmp (g_peer->update_if, peer->update_if) != 0)
4984           vty_out (vty, " neighbor %s update-source %s%s", addr,
4985                    peer->update_if, VTY_NEWLINE);
4986       if (peer->update_source)
4987         if (! peer_group_active (peer) || ! g_peer->update_source
4988             || sockunion_cmp (g_peer->update_source,
4989                               peer->update_source) != 0)
4990           vty_out (vty, " neighbor %s update-source %s%s", addr,
4991                    sockunion2str (peer->update_source, buf, SU_ADDRSTRLEN),
4992                    VTY_NEWLINE);
4993
4994       /* advertisement-interval */
4995       if (CHECK_FLAG (peer->config, PEER_CONFIG_ROUTEADV) &&
4996           ! peer_group_active (peer))
4997         vty_out (vty, " neighbor %s advertisement-interval %d%s",
4998                  addr, peer->v_routeadv, VTY_NEWLINE); 
4999
5000       /* timers. */
5001       if (CHECK_FLAG (peer->config, PEER_CONFIG_TIMER)
5002           && ! peer_group_active (peer))
5003           vty_out (vty, " neighbor %s timers %d %d%s", addr, 
5004           peer->keepalive, peer->holdtime, VTY_NEWLINE);
5005
5006       if (CHECK_FLAG (peer->config, PEER_CONFIG_CONNECT) &&
5007           ! peer_group_active (peer))
5008           vty_out (vty, " neighbor %s timers connect %d%s", addr, 
5009           peer->connect, VTY_NEWLINE);
5010
5011       /* Default weight. */
5012       if (CHECK_FLAG (peer->config, PEER_CONFIG_WEIGHT))
5013         if (! peer_group_active (peer) ||
5014             g_peer->weight != peer->weight)
5015           vty_out (vty, " neighbor %s weight %d%s", addr, peer->weight,
5016                    VTY_NEWLINE);
5017
5018       /* Dynamic capability.  */
5019       if (CHECK_FLAG (peer->flags, PEER_FLAG_DYNAMIC_CAPABILITY))
5020         if (! peer_group_active (peer) ||
5021             ! CHECK_FLAG (g_peer->flags, PEER_FLAG_DYNAMIC_CAPABILITY))
5022         vty_out (vty, " neighbor %s capability dynamic%s", addr,
5023              VTY_NEWLINE);
5024
5025       /* dont capability negotiation. */
5026       if (CHECK_FLAG (peer->flags, PEER_FLAG_DONT_CAPABILITY))
5027         if (! peer_group_active (peer) ||
5028             ! CHECK_FLAG (g_peer->flags, PEER_FLAG_DONT_CAPABILITY))
5029         vty_out (vty, " neighbor %s dont-capability-negotiate%s", addr,
5030                  VTY_NEWLINE);
5031
5032       /* override capability negotiation. */
5033       if (CHECK_FLAG (peer->flags, PEER_FLAG_OVERRIDE_CAPABILITY))
5034         if (! peer_group_active (peer) ||
5035             ! CHECK_FLAG (g_peer->flags, PEER_FLAG_OVERRIDE_CAPABILITY))
5036         vty_out (vty, " neighbor %s override-capability%s", addr,
5037                  VTY_NEWLINE);
5038
5039       /* strict capability negotiation. */
5040       if (CHECK_FLAG (peer->flags, PEER_FLAG_STRICT_CAP_MATCH))
5041         if (! peer_group_active (peer) ||
5042             ! CHECK_FLAG (g_peer->flags, PEER_FLAG_STRICT_CAP_MATCH))
5043         vty_out (vty, " neighbor %s strict-capability-match%s", addr,
5044              VTY_NEWLINE);
5045
5046       if (! peer->af_group[AFI_IP][SAFI_UNICAST])
5047         {
5048           if (bgp_flag_check (bgp, BGP_FLAG_NO_DEFAULT_IPV4))
5049             {
5050               if (peer->afc[AFI_IP][SAFI_UNICAST])
5051                 vty_out (vty, " neighbor %s activate%s", addr, VTY_NEWLINE);
5052             }
5053           else
5054             {
5055               if (! peer->afc[AFI_IP][SAFI_UNICAST])
5056                 vty_out (vty, " no neighbor %s activate%s", addr, VTY_NEWLINE);
5057             }
5058         }
5059     }
5060
5061
5062   /************************************
5063    ****** Per AF to the neighbor ******
5064    ************************************/
5065
5066   if (! (afi == AFI_IP && safi == SAFI_UNICAST))
5067     {
5068       if (peer->af_group[afi][safi])
5069         vty_out (vty, " neighbor %s peer-group %s%s", addr,
5070                  peer->group->name, VTY_NEWLINE);
5071       else
5072         vty_out (vty, " neighbor %s activate%s", addr, VTY_NEWLINE);
5073     }
5074
5075   /* ORF capability.  */
5076   if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ORF_PREFIX_SM)
5077       || CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ORF_PREFIX_RM))
5078     if (! peer->af_group[afi][safi])
5079     {
5080       vty_out (vty, " neighbor %s capability orf prefix-list", addr);
5081
5082       if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ORF_PREFIX_SM)
5083           && CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ORF_PREFIX_RM))
5084         vty_out (vty, " both");
5085       else if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_ORF_PREFIX_SM))
5086         vty_out (vty, " send");
5087       else
5088         vty_out (vty, " receive");
5089       vty_out (vty, "%s", VTY_NEWLINE);
5090     }
5091
5092   /* Route reflector client. */
5093   if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_REFLECTOR_CLIENT)
5094       && ! peer->af_group[afi][safi])
5095     vty_out (vty, " neighbor %s route-reflector-client%s", addr, 
5096              VTY_NEWLINE);
5097
5098   /* Nexthop self. */
5099   if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_NEXTHOP_SELF)
5100       && ! peer->af_group[afi][safi])
5101     vty_out (vty, " neighbor %s next-hop-self%s%s", addr,
5102              peer_af_flag_check (peer, afi, safi, PEER_FLAG_NEXTHOP_SELF_ALL) ?
5103              " all" : "", VTY_NEWLINE);
5104
5105   /* Remove private AS. */
5106   if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_REMOVE_PRIVATE_AS)
5107       && ! peer->af_group[afi][safi])
5108     vty_out (vty, " neighbor %s remove-private-AS%s",
5109              addr, VTY_NEWLINE);
5110
5111   /* send-community print. */
5112   if (! peer->af_group[afi][safi])
5113     {
5114       if (bgp_option_check (BGP_OPT_CONFIG_CISCO))
5115         {
5116           if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_COMMUNITY)
5117               && peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_EXT_COMMUNITY)
5118               && peer_af_flag_check(peer, afi, safi, PEER_FLAG_SEND_LARGE_COMMUNITY))
5119             vty_out (vty, " neighbor %s send-community all%s", addr, VTY_NEWLINE);
5120           else if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_EXT_COMMUNITY))  
5121             vty_out (vty, " neighbor %s send-community extended%s",
5122                      addr, VTY_NEWLINE);
5123           else if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_LARGE_COMMUNITY))
5124             vty_out (vty, " neighbor %s send-community large%s",
5125                      addr, VTY_NEWLINE);
5126           else if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_COMMUNITY))
5127             vty_out (vty, " neighbor %s send-community%s", addr, VTY_NEWLINE);
5128         }
5129       else
5130         {
5131           if (! peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_COMMUNITY)
5132               && ! peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_EXT_COMMUNITY)
5133               && ! peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_LARGE_COMMUNITY))
5134             vty_out (vty, " no neighbor %s send-community all%s",
5135                      addr, VTY_NEWLINE);
5136           else if (! peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_EXT_COMMUNITY))
5137             vty_out (vty, " no neighbor %s send-community extended%s",
5138                      addr, VTY_NEWLINE);
5139           else if (! peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_LARGE_COMMUNITY))
5140             vty_out (vty, " no neighbor %s send-community large%s",
5141                      addr, VTY_NEWLINE);
5142           else if (! peer_af_flag_check (peer, afi, safi, PEER_FLAG_SEND_COMMUNITY))
5143             vty_out (vty, " no neighbor %s send-community%s",
5144                      addr, VTY_NEWLINE);
5145         }
5146     }
5147
5148   /* Default information */
5149   if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_DEFAULT_ORIGINATE)
5150       && ! peer->af_group[afi][safi])
5151     {
5152       vty_out (vty, " neighbor %s default-originate", addr);
5153       if (peer->default_rmap[afi][safi].name)
5154         vty_out (vty, " route-map %s", peer->default_rmap[afi][safi].name);
5155       vty_out (vty, "%s", VTY_NEWLINE);
5156     }
5157
5158   /* Soft reconfiguration inbound. */
5159   if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_SOFT_RECONFIG))
5160     if (! peer->af_group[afi][safi] ||
5161         ! CHECK_FLAG (g_peer->af_flags[afi][safi], PEER_FLAG_SOFT_RECONFIG))
5162     vty_out (vty, " neighbor %s soft-reconfiguration inbound%s", addr,
5163              VTY_NEWLINE);
5164
5165   /* maximum-prefix. */
5166   if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX))
5167     if (! peer->af_group[afi][safi]
5168         || g_peer->pmax[afi][safi] != peer->pmax[afi][safi]
5169         || g_peer->pmax_threshold[afi][safi] != peer->pmax_threshold[afi][safi]
5170         || CHECK_FLAG (g_peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING)
5171            != CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING))
5172       {
5173         vty_out (vty, " neighbor %s maximum-prefix %ld", addr, peer->pmax[afi][safi]);
5174         if (peer->pmax_threshold[afi][safi] != MAXIMUM_PREFIX_THRESHOLD_DEFAULT)
5175           vty_out (vty, " %d", peer->pmax_threshold[afi][safi]);
5176         if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MAX_PREFIX_WARNING))
5177           vty_out (vty, " warning-only");
5178         if (peer->pmax_restart[afi][safi])
5179           vty_out (vty, " restart %d", peer->pmax_restart[afi][safi]);
5180         vty_out (vty, "%s", VTY_NEWLINE);
5181       }
5182
5183   /* Route server client. */
5184   if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_RSERVER_CLIENT)
5185       && ! peer->af_group[afi][safi])
5186     vty_out (vty, " neighbor %s route-server-client%s", addr, VTY_NEWLINE);
5187
5188   /* Nexthop-local unchanged. */
5189   if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_NEXTHOP_LOCAL_UNCHANGED)
5190       && ! peer->af_group[afi][safi])
5191     vty_out (vty, " neighbor %s nexthop-local unchanged%s", addr, VTY_NEWLINE);
5192
5193   /* Allow AS in.  */
5194   if (peer_af_flag_check (peer, afi, safi, PEER_FLAG_ALLOWAS_IN))
5195     if (! peer_group_active (peer)
5196         || ! peer_af_flag_check (g_peer, afi, safi, PEER_FLAG_ALLOWAS_IN)
5197         || peer->allowas_in[afi][safi] != g_peer->allowas_in[afi][safi])
5198       {
5199         if (peer->allowas_in[afi][safi] == 3)
5200           vty_out (vty, " neighbor %s allowas-in%s", addr, VTY_NEWLINE);
5201         else
5202           vty_out (vty, " neighbor %s allowas-in %d%s", addr,
5203                    peer->allowas_in[afi][safi], VTY_NEWLINE);
5204       }
5205
5206   /* Filter. */
5207   bgp_config_write_filter (vty, peer, afi, safi);
5208
5209   /* atribute-unchanged. */
5210   if ((CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_AS_PATH_UNCHANGED)
5211       || CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_NEXTHOP_UNCHANGED)
5212       || CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MED_UNCHANGED))
5213       && ! peer->af_group[afi][safi])
5214     {
5215       if (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_AS_PATH_UNCHANGED)
5216           && CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_NEXTHOP_UNCHANGED)
5217           && CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MED_UNCHANGED))
5218         vty_out (vty, " neighbor %s attribute-unchanged%s", addr, VTY_NEWLINE);
5219       else
5220         vty_out (vty, " neighbor %s attribute-unchanged%s%s%s%s", addr, 
5221              (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_AS_PATH_UNCHANGED)) ?
5222              " as-path" : "",
5223              (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_NEXTHOP_UNCHANGED)) ?
5224              " next-hop" : "",
5225              (CHECK_FLAG (peer->af_flags[afi][safi], PEER_FLAG_MED_UNCHANGED)) ?
5226              " med" : "", VTY_NEWLINE);
5227     }
5228 }
5229
5230 /* Display "address-family" configuration header. */
5231 void
5232 bgp_config_write_family_header (struct vty *vty, afi_t afi, safi_t safi,
5233                                 int *write)
5234 {
5235   if (*write)
5236     return;
5237
5238   if (afi == AFI_IP && safi == SAFI_UNICAST)
5239     return;
5240
5241   vty_out (vty, "!%s address-family ", VTY_NEWLINE);
5242
5243   if (afi == AFI_IP)
5244     {
5245       if (safi == SAFI_MULTICAST)
5246         vty_out (vty, "ipv4 multicast");
5247       else if (safi == SAFI_MPLS_VPN)
5248         vty_out (vty, "vpnv4");
5249       else if (safi == SAFI_ENCAP)
5250         vty_out (vty, "encap");
5251     }
5252   else if (afi == AFI_IP6)
5253     {
5254       if (safi == SAFI_MPLS_VPN)
5255         vty_out (vty, "vpnv6");
5256       else if (safi == SAFI_ENCAP)
5257         vty_out (vty, "encapv6");
5258       else
5259         {
5260           vty_out (vty, "ipv6");
5261           if (safi == SAFI_MULTICAST)
5262             vty_out (vty, " multicast");
5263         }
5264     }
5265
5266   vty_out (vty, "%s", VTY_NEWLINE);
5267
5268   *write = 1;
5269 }
5270
5271 /* Address family based peer configuration display.  */
5272 static int
5273 bgp_config_write_family (struct vty *vty, struct bgp *bgp, afi_t afi,
5274                          safi_t safi)
5275 {
5276   int write = 0;
5277   struct peer *peer;
5278   struct peer_group *group;
5279   struct listnode *node, *nnode;
5280
5281   bgp_config_write_network (vty, bgp, afi, safi, &write);
5282
5283   bgp_config_write_redistribute (vty, bgp, afi, safi, &write);
5284
5285   for (ALL_LIST_ELEMENTS (bgp->group, node, nnode, group))
5286     {
5287       if (group->conf->afc[afi][safi])
5288         {
5289           bgp_config_write_family_header (vty, afi, safi, &write);
5290           bgp_config_write_peer (vty, bgp, group->conf, afi, safi);
5291         }
5292     }
5293   for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
5294     {
5295       if (peer->afc[afi][safi])
5296         {
5297           if (! CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
5298             {
5299               bgp_config_write_family_header (vty, afi, safi, &write);
5300               bgp_config_write_peer (vty, bgp, peer, afi, safi);
5301             }
5302         }
5303     }
5304
5305   bgp_config_write_maxpaths (vty, bgp, afi, safi, &write);
5306
5307   bgp_config_write_distance (vty, bgp, afi, safi, &write);
5308
5309   if (write)
5310     vty_out (vty, " exit-address-family%s", VTY_NEWLINE);
5311
5312   return write;
5313 }
5314
5315 int
5316 bgp_config_write (struct vty *vty)
5317 {
5318   int write = 0;
5319   struct bgp *bgp;
5320   struct peer_group *group;
5321   struct peer *peer;
5322   struct listnode *node, *nnode;
5323   struct listnode *mnode, *mnnode;
5324
5325   /* BGP Multiple instance. */
5326   if (bgp_option_check (BGP_OPT_MULTIPLE_INSTANCE))
5327     {    
5328       vty_out (vty, "bgp multiple-instance%s", VTY_NEWLINE);
5329       write++;
5330     }
5331
5332   /* BGP Config type. */
5333   if (bgp_option_check (BGP_OPT_CONFIG_CISCO))
5334     {    
5335       vty_out (vty, "bgp config-type cisco%s", VTY_NEWLINE);
5336       write++;
5337     }
5338
5339   /* BGP configuration. */
5340   for (ALL_LIST_ELEMENTS (bm->bgp, mnode, mnnode, bgp))
5341     {
5342       if (write)
5343         vty_out (vty, "!%s", VTY_NEWLINE);
5344
5345       /* Router bgp ASN */
5346       vty_out (vty, "router bgp %u", bgp->as);
5347
5348       if (bgp_option_check (BGP_OPT_MULTIPLE_INSTANCE))
5349         {
5350           if (bgp->name)
5351             vty_out (vty, " view %s", bgp->name);
5352         }
5353       vty_out (vty, "%s", VTY_NEWLINE);
5354
5355       /* No Synchronization */
5356       if (bgp_option_check (BGP_OPT_CONFIG_CISCO))
5357         vty_out (vty, " no synchronization%s", VTY_NEWLINE);
5358
5359       /* BGP fast-external-failover. */
5360       if (CHECK_FLAG (bgp->flags, BGP_FLAG_NO_FAST_EXT_FAILOVER))
5361         vty_out (vty, " no bgp fast-external-failover%s", VTY_NEWLINE); 
5362
5363       /* BGP router ID. */
5364       if (CHECK_FLAG (bgp->config, BGP_CONFIG_ROUTER_ID))
5365         vty_out (vty, " bgp router-id %s%s", inet_ntoa (bgp->router_id), 
5366                  VTY_NEWLINE);
5367
5368       /* BGP log-neighbor-changes. */
5369       if (!bgp_flag_check (bgp, BGP_FLAG_LOG_NEIGHBOR_CHANGES))
5370         vty_out (vty, " no bgp log-neighbor-changes%s", VTY_NEWLINE);
5371
5372       /* BGP configuration. */
5373       if (bgp_flag_check (bgp, BGP_FLAG_ALWAYS_COMPARE_MED))
5374         vty_out (vty, " bgp always-compare-med%s", VTY_NEWLINE);
5375
5376       /* BGP default ipv4-unicast. */
5377       if (bgp_flag_check (bgp, BGP_FLAG_NO_DEFAULT_IPV4))
5378         vty_out (vty, " no bgp default ipv4-unicast%s", VTY_NEWLINE);
5379
5380       /* BGP default local-preference. */
5381       if (bgp->default_local_pref != BGP_DEFAULT_LOCAL_PREF)
5382         vty_out (vty, " bgp default local-preference %d%s",
5383                  bgp->default_local_pref, VTY_NEWLINE);
5384
5385       /* BGP client-to-client reflection. */
5386       if (bgp_flag_check (bgp, BGP_FLAG_NO_CLIENT_TO_CLIENT))
5387         vty_out (vty, " no bgp client-to-client reflection%s", VTY_NEWLINE);
5388       
5389       /* BGP cluster ID. */
5390       if (CHECK_FLAG (bgp->config, BGP_CONFIG_CLUSTER_ID))
5391         vty_out (vty, " bgp cluster-id %s%s", inet_ntoa (bgp->cluster_id),
5392                  VTY_NEWLINE);
5393
5394       /* Confederation identifier*/
5395       if (CHECK_FLAG (bgp->config, BGP_CONFIG_CONFEDERATION))
5396        vty_out (vty, " bgp confederation identifier %i%s", bgp->confed_id,
5397                 VTY_NEWLINE);
5398
5399       /* Confederation peer */
5400       if (bgp->confed_peers_cnt > 0)
5401         {
5402           int i;
5403
5404           vty_out (vty, " bgp confederation peers");
5405
5406          for (i = 0; i < bgp->confed_peers_cnt; i++)
5407            vty_out(vty, " %u", bgp->confed_peers[i]);
5408
5409           vty_out (vty, "%s", VTY_NEWLINE);
5410         }
5411
5412       /* BGP enforce-first-as. */
5413       if (bgp_flag_check (bgp, BGP_FLAG_ENFORCE_FIRST_AS))
5414         vty_out (vty, " bgp enforce-first-as%s", VTY_NEWLINE);
5415
5416       /* BGP deterministic-med. */
5417       if (bgp_flag_check (bgp, BGP_FLAG_DETERMINISTIC_MED))
5418         vty_out (vty, " bgp deterministic-med%s", VTY_NEWLINE);
5419
5420       /* BGP graceful-restart. */
5421       if (bgp->stalepath_time != BGP_DEFAULT_STALEPATH_TIME)
5422         vty_out (vty, " bgp graceful-restart stalepath-time %d%s",
5423                  bgp->stalepath_time, VTY_NEWLINE);
5424       if (bgp->restart_time != BGP_DEFAULT_RESTART_TIME)
5425         vty_out (vty, " bgp graceful-restart restart-time %d%s",
5426                  bgp->restart_time, VTY_NEWLINE);
5427       if (bgp_flag_check (bgp, BGP_FLAG_GRACEFUL_RESTART))
5428        vty_out (vty, " bgp graceful-restart%s", VTY_NEWLINE);
5429
5430       /* BGP bestpath method. */
5431       if (bgp_flag_check (bgp, BGP_FLAG_ASPATH_IGNORE))
5432         vty_out (vty, " bgp bestpath as-path ignore%s", VTY_NEWLINE);
5433       if (bgp_flag_check (bgp, BGP_FLAG_ASPATH_CONFED))
5434         vty_out (vty, " bgp bestpath as-path confed%s", VTY_NEWLINE);
5435       if (bgp_flag_check (bgp, BGP_FLAG_ASPATH_MULTIPATH_RELAX)) {
5436         vty_out (vty, " bgp bestpath as-path multipath-relax%s", VTY_NEWLINE);
5437       }
5438       if (bgp_flag_check (bgp, BGP_FLAG_RR_ALLOW_OUTBOUND_POLICY)) {
5439         vty_out (vty, " bgp route-reflector allow-outbound-policy%s",
5440                  VTY_NEWLINE);
5441       }
5442       if (bgp_flag_check (bgp, BGP_FLAG_COMPARE_ROUTER_ID))
5443         vty_out (vty, " bgp bestpath compare-routerid%s", VTY_NEWLINE);
5444       if (bgp_flag_check (bgp, BGP_FLAG_MED_CONFED)
5445           || bgp_flag_check (bgp, BGP_FLAG_MED_MISSING_AS_WORST))
5446         {
5447           vty_out (vty, " bgp bestpath med");
5448           if (bgp_flag_check (bgp, BGP_FLAG_MED_CONFED))
5449             vty_out (vty, " confed");
5450           if (bgp_flag_check (bgp, BGP_FLAG_MED_MISSING_AS_WORST))
5451             vty_out (vty, " missing-as-worst");
5452           vty_out (vty, "%s", VTY_NEWLINE);
5453         }
5454
5455       /* BGP network import check. */
5456       if (bgp_flag_check (bgp, BGP_FLAG_IMPORT_CHECK))
5457         vty_out (vty, " bgp network import-check%s", VTY_NEWLINE);
5458
5459       /* BGP flag dampening. */
5460       if (CHECK_FLAG (bgp->af_flags[AFI_IP][SAFI_UNICAST],
5461           BGP_CONFIG_DAMPENING))
5462         bgp_config_write_damp (vty);
5463
5464       /* BGP static route configuration. */
5465       bgp_config_write_network (vty, bgp, AFI_IP, SAFI_UNICAST, &write);
5466
5467       /* BGP redistribute configuration. */
5468       bgp_config_write_redistribute (vty, bgp, AFI_IP, SAFI_UNICAST, &write);
5469
5470       /* BGP timers configuration. */
5471       if (bgp->default_keepalive != BGP_DEFAULT_KEEPALIVE
5472           && bgp->default_holdtime != BGP_DEFAULT_HOLDTIME)
5473         vty_out (vty, " timers bgp %d %d%s", bgp->default_keepalive, 
5474                  bgp->default_holdtime, VTY_NEWLINE);
5475
5476       /* peer-group */
5477       for (ALL_LIST_ELEMENTS (bgp->group, node, nnode, group))
5478         {
5479           bgp_config_write_peer (vty, bgp, group->conf, AFI_IP, SAFI_UNICAST);
5480         }
5481
5482       /* Normal neighbor configuration. */
5483       for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
5484         {
5485           if (! CHECK_FLAG (peer->sflags, PEER_STATUS_ACCEPT_PEER))
5486             bgp_config_write_peer (vty, bgp, peer, AFI_IP, SAFI_UNICAST);
5487         }
5488
5489       /* maximum-paths */
5490       bgp_config_write_maxpaths (vty, bgp, AFI_IP, SAFI_UNICAST, &write);
5491
5492       /* Distance configuration. */
5493       bgp_config_write_distance (vty, bgp, AFI_IP, SAFI_UNICAST, &write);
5494       
5495       /* No auto-summary */
5496       if (bgp_option_check (BGP_OPT_CONFIG_CISCO))
5497         vty_out (vty, " no auto-summary%s", VTY_NEWLINE);
5498
5499       /* IPv4 multicast configuration.  */
5500       write += bgp_config_write_family (vty, bgp, AFI_IP, SAFI_MULTICAST);
5501
5502       /* IPv4 VPN configuration.  */
5503       write += bgp_config_write_family (vty, bgp, AFI_IP, SAFI_MPLS_VPN);
5504
5505       /* ENCAPv4 configuration.  */
5506       write += bgp_config_write_family (vty, bgp, AFI_IP, SAFI_ENCAP);
5507
5508       /* IPv6 unicast configuration.  */
5509       write += bgp_config_write_family (vty, bgp, AFI_IP6, SAFI_UNICAST);
5510
5511       /* IPv6 multicast configuration.  */
5512       write += bgp_config_write_family (vty, bgp, AFI_IP6, SAFI_MULTICAST);
5513
5514       /* IPv6 VPN configuration.  */
5515       write += bgp_config_write_family (vty, bgp, AFI_IP6, SAFI_MPLS_VPN);
5516
5517       /* ENCAPv6 configuration.  */
5518       write += bgp_config_write_family (vty, bgp, AFI_IP6, SAFI_ENCAP);
5519
5520       vty_out (vty, " exit%s", VTY_NEWLINE);
5521
5522       write++;
5523     }
5524   return write;
5525 }
5526
5527 void
5528 bgp_master_init (void)
5529 {
5530   memset (&bgp_master, 0, sizeof (struct bgp_master));
5531
5532   bm = &bgp_master;
5533   bm->bgp = list_new ();
5534   bm->listen_sockets = list_new ();
5535   bm->port = BGP_PORT_DEFAULT;
5536   bm->master = thread_master_create ();
5537   bm->start_time = bgp_clock ();
5538 }
5539
5540
5541 void
5542 bgp_init (void)
5543 {
5544
5545   /* allocates some vital data structures used by peer commands in vty_init */
5546   bgp_scan_init ();
5547
5548   /* Init zebra. */
5549   bgp_zebra_init (bm->master);
5550
5551   /* BGP VTY commands installation.  */
5552   bgp_vty_init ();
5553
5554   /* BGP inits. */
5555   bgp_attr_init ();
5556   bgp_debug_init ();
5557   bgp_dump_init ();
5558   bgp_route_init ();
5559   bgp_route_map_init ();
5560   bgp_address_init ();
5561   bgp_scan_vty_init();
5562   bgp_mplsvpn_init ();
5563   bgp_encap_init ();
5564
5565   /* Access list initialize. */
5566   access_list_init ();
5567   access_list_add_hook (peer_distribute_update);
5568   access_list_delete_hook (peer_distribute_update);
5569
5570   /* Filter list initialize. */
5571   bgp_filter_init ();
5572   as_list_add_hook (peer_aslist_update);
5573   as_list_delete_hook (peer_aslist_update);
5574
5575   /* Prefix list initialize.*/
5576   prefix_list_init ();
5577   prefix_list_add_hook (peer_prefix_list_update);
5578   prefix_list_delete_hook (peer_prefix_list_update);
5579
5580   /* Community list initialize. */
5581   bgp_clist = community_list_init ();
5582
5583 #ifdef HAVE_SNMP
5584   bgp_snmp_init ();
5585 #endif /* HAVE_SNMP */
5586 }
5587
5588 void
5589 bgp_terminate (void)
5590 {
5591   struct bgp *bgp;
5592   struct peer *peer;
5593   struct listnode *node, *nnode;
5594   struct listnode *mnode, *mnnode;
5595
5596   for (ALL_LIST_ELEMENTS (bm->bgp, mnode, mnnode, bgp))
5597     for (ALL_LIST_ELEMENTS (bgp->peer, node, nnode, peer))
5598       if (peer->status == Established)
5599           bgp_notify_send (peer, BGP_NOTIFY_CEASE,
5600                            BGP_NOTIFY_CEASE_PEER_UNCONFIG);
5601   
5602   bgp_cleanup_routes ();
5603   
5604   if (bm->process_main_queue)
5605     {
5606       work_queue_free (bm->process_main_queue);
5607       bm->process_main_queue = NULL;
5608     }
5609   if (bm->process_rsclient_queue)
5610     {
5611       work_queue_free (bm->process_rsclient_queue);
5612       bm->process_rsclient_queue = NULL;
5613     }
5614 }