paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 1 | /* BGP attributes. |
| 2 | Copyright (C) 1996, 97, 98 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 | |
paul | 00d252c | 2005-05-23 14:19:54 +0000 | [diff] [blame] | 21 | #ifndef _QUAGGA_BGP_ATTR_H |
| 22 | #define _QUAGGA_BGP_ATTR_H |
| 23 | |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 24 | /* Simple bit mapping. */ |
| 25 | #define BITMAP_NBBY 8 |
| 26 | |
| 27 | #define SET_BITMAP(MAP, NUM) \ |
| 28 | SET_FLAG (MAP[(NUM) / BITMAP_NBBY], 1 << ((NUM) % BITMAP_NBBY)) |
| 29 | |
| 30 | #define CHECK_BITMAP(MAP, NUM) \ |
| 31 | CHECK_FLAG (MAP[(NUM) / BITMAP_NBBY], 1 << ((NUM) % BITMAP_NBBY)) |
| 32 | |
paul | 3b42497 | 2003-10-13 09:47:32 +0000 | [diff] [blame] | 33 | #define BGP_MED_MAX UINT32_MAX |
| 34 | |
Paul Jakma | 03e214c | 2007-04-29 18:31:07 +0000 | [diff] [blame] | 35 | |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 36 | /* BGP Attribute type range. */ |
| 37 | #define BGP_ATTR_TYPE_RANGE 256 |
| 38 | #define BGP_ATTR_BITMAP_SIZE (BGP_ATTR_TYPE_RANGE / BITMAP_NBBY) |
| 39 | |
| 40 | /* BGP Attribute flags. */ |
| 41 | #define BGP_ATTR_FLAG_OPTIONAL 0x80 /* Attribute is optional. */ |
| 42 | #define BGP_ATTR_FLAG_TRANS 0x40 /* Attribute is transitive. */ |
| 43 | #define BGP_ATTR_FLAG_PARTIAL 0x20 /* Attribute is partial. */ |
| 44 | #define BGP_ATTR_FLAG_EXTLEN 0x10 /* Extended length flag. */ |
| 45 | |
| 46 | /* BGP attribute header must bigger than 2. */ |
Paul Jakma | 370b64a | 2007-12-22 16:49:52 +0000 | [diff] [blame] | 47 | #define BGP_ATTR_MIN_LEN 3 /* Attribute flag, type length. */ |
Paul Jakma | 03e214c | 2007-04-29 18:31:07 +0000 | [diff] [blame] | 48 | #define BGP_ATTR_DEFAULT_WEIGHT 32768 |
| 49 | |
Lou Berger | c374178 | 2016-01-12 13:42:01 -0500 | [diff] [blame] | 50 | struct bgp_attr_encap_subtlv { |
| 51 | struct bgp_attr_encap_subtlv *next; /* for chaining */ |
| 52 | uint16_t type; |
| 53 | uint16_t length; |
| 54 | uint8_t value[1]; /* will be extended */ |
| 55 | }; |
| 56 | |
Paul Jakma | fb982c2 | 2007-05-04 20:15:47 +0000 | [diff] [blame] | 57 | /* Additional/uncommon BGP attributes. |
| 58 | * lazily allocated as and when a struct attr |
| 59 | * requires it. |
| 60 | */ |
| 61 | struct attr_extra |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 62 | { |
Paul Jakma | fb982c2 | 2007-05-04 20:15:47 +0000 | [diff] [blame] | 63 | /* Multi-Protocol Nexthop, AFI IPv6 */ |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 64 | struct in6_addr mp_nexthop_global; |
| 65 | struct in6_addr mp_nexthop_local; |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 66 | |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 67 | /* Extended Communities attribute. */ |
| 68 | struct ecommunity *ecommunity; |
Paul Jakma | cbdfbaa | 2006-03-30 13:20:48 +0000 | [diff] [blame] | 69 | |
| 70 | /* Route-Reflector Cluster attribute */ |
| 71 | struct cluster_list *cluster; |
| 72 | |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 73 | /* Unknown transitive attribute. */ |
| 74 | struct transit *transit; |
Paul Jakma | cbdfbaa | 2006-03-30 13:20:48 +0000 | [diff] [blame] | 75 | |
Paul Jakma | fb982c2 | 2007-05-04 20:15:47 +0000 | [diff] [blame] | 76 | struct in_addr mp_nexthop_global_in; |
Paul Jakma | fb982c2 | 2007-05-04 20:15:47 +0000 | [diff] [blame] | 77 | |
| 78 | /* Aggregator Router ID attribute */ |
| 79 | struct in_addr aggregator_addr; |
| 80 | |
| 81 | /* Route Reflector Originator attribute */ |
| 82 | struct in_addr originator_id; |
| 83 | |
| 84 | /* Local weight, not actually an attribute */ |
| 85 | u_int32_t weight; |
| 86 | |
| 87 | /* Aggregator ASN */ |
| 88 | as_t aggregator_as; |
| 89 | |
| 90 | /* MP Nexthop length */ |
| 91 | u_char mp_nexthop_len; |
Lou Berger | c374178 | 2016-01-12 13:42:01 -0500 | [diff] [blame] | 92 | |
| 93 | uint16_t encap_tunneltype; /* grr */ |
| 94 | struct bgp_attr_encap_subtlv *encap_subtlvs; /* rfc5512 */ |
Paul Jakma | fb982c2 | 2007-05-04 20:15:47 +0000 | [diff] [blame] | 95 | }; |
| 96 | |
| 97 | /* BGP core attribute structure. */ |
| 98 | struct attr |
| 99 | { |
| 100 | /* AS Path structure */ |
| 101 | struct aspath *aspath; |
| 102 | |
| 103 | /* Community structure */ |
| 104 | struct community *community; |
| 105 | |
| 106 | /* Lazily allocated pointer to extra attributes */ |
| 107 | struct attr_extra *extra; |
| 108 | |
Paul Jakma | cbdfbaa | 2006-03-30 13:20:48 +0000 | [diff] [blame] | 109 | /* Reference count of this attribute. */ |
| 110 | unsigned long refcnt; |
| 111 | |
| 112 | /* Flag of attribute is set or not. */ |
| 113 | u_int32_t flag; |
| 114 | |
| 115 | /* Apart from in6_addr, the remaining static attributes */ |
| 116 | struct in_addr nexthop; |
| 117 | u_int32_t med; |
| 118 | u_int32_t local_pref; |
Paul Jakma | 4136717 | 2007-08-06 15:24:51 +0000 | [diff] [blame] | 119 | |
Paul Jakma | fb982c2 | 2007-05-04 20:15:47 +0000 | [diff] [blame] | 120 | /* Path origin attribute */ |
Paul Jakma | cbdfbaa | 2006-03-30 13:20:48 +0000 | [diff] [blame] | 121 | u_char origin; |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 122 | }; |
| 123 | |
| 124 | /* Router Reflector related structure. */ |
| 125 | struct cluster_list |
| 126 | { |
| 127 | unsigned long refcnt; |
| 128 | int length; |
| 129 | struct in_addr *list; |
| 130 | }; |
| 131 | |
| 132 | /* Unknown transit attribute. */ |
| 133 | struct transit |
| 134 | { |
| 135 | unsigned long refcnt; |
| 136 | int length; |
| 137 | u_char *val; |
| 138 | }; |
| 139 | |
| 140 | #define ATTR_FLAG_BIT(X) (1 << ((X) - 1)) |
| 141 | |
Paul Jakma | b881c70 | 2010-11-23 16:35:42 +0000 | [diff] [blame] | 142 | typedef enum { |
| 143 | BGP_ATTR_PARSE_PROCEED = 0, |
| 144 | BGP_ATTR_PARSE_ERROR = -1, |
| 145 | BGP_ATTR_PARSE_WITHDRAW = -2, |
David Lamparter | f57000c | 2014-06-04 01:01:10 +0200 | [diff] [blame] | 146 | |
| 147 | /* only used internally, send notify + convert to BGP_ATTR_PARSE_ERROR */ |
| 148 | BGP_ATTR_PARSE_ERROR_NOTIFYPLS = -3, |
Paul Jakma | b881c70 | 2010-11-23 16:35:42 +0000 | [diff] [blame] | 149 | } bgp_attr_parse_ret_t; |
| 150 | |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 151 | /* Prototypes. */ |
paul | 94f2b39 | 2005-06-28 12:44:16 +0000 | [diff] [blame] | 152 | extern void bgp_attr_init (void); |
Chris Caputo | 228da42 | 2009-07-18 05:44:03 +0000 | [diff] [blame] | 153 | extern void bgp_attr_finish (void); |
Paul Jakma | b881c70 | 2010-11-23 16:35:42 +0000 | [diff] [blame] | 154 | extern bgp_attr_parse_ret_t bgp_attr_parse (struct peer *, struct attr *, |
| 155 | bgp_size_t, struct bgp_nlri *, |
| 156 | struct bgp_nlri *); |
Paul Jakma | fb982c2 | 2007-05-04 20:15:47 +0000 | [diff] [blame] | 157 | extern struct attr_extra *bgp_attr_extra_get (struct attr *); |
| 158 | extern void bgp_attr_extra_free (struct attr *); |
| 159 | extern void bgp_attr_dup (struct attr *, struct attr *); |
paul | 94f2b39 | 2005-06-28 12:44:16 +0000 | [diff] [blame] | 160 | extern struct attr *bgp_attr_intern (struct attr *attr); |
Paul Jakma | b881c70 | 2010-11-23 16:35:42 +0000 | [diff] [blame] | 161 | extern void bgp_attr_unintern_sub (struct attr *); |
Paul Jakma | f6f434b | 2010-11-23 21:28:03 +0000 | [diff] [blame] | 162 | extern void bgp_attr_unintern (struct attr **); |
paul | 94f2b39 | 2005-06-28 12:44:16 +0000 | [diff] [blame] | 163 | extern void bgp_attr_flush (struct attr *); |
| 164 | extern struct attr *bgp_attr_default_set (struct attr *attr, u_char); |
| 165 | extern struct attr *bgp_attr_default_intern (u_char); |
| 166 | extern struct attr *bgp_attr_aggregate_intern (struct bgp *, u_char, |
paul | 5228ad2 | 2004-06-04 17:58:18 +0000 | [diff] [blame] | 167 | struct aspath *, |
| 168 | struct community *, int as_set); |
Pradosh Mohapatra | 8c71e48 | 2014-01-15 06:57:57 +0000 | [diff] [blame] | 169 | extern bgp_size_t bgp_packet_attribute (struct bgp *bgp, struct peer *, |
| 170 | struct stream *, struct attr *, |
| 171 | struct prefix *, afi_t, safi_t, |
| 172 | struct peer *, struct prefix_rd *, |
| 173 | u_char *); |
paul | 94f2b39 | 2005-06-28 12:44:16 +0000 | [diff] [blame] | 174 | extern void bgp_dump_routes_attr (struct stream *, struct attr *, |
| 175 | struct prefix *); |
Stephen Hemminger | ffe11cf | 2008-08-14 16:25:25 +0100 | [diff] [blame] | 176 | extern int attrhash_cmp (const void *, const void *); |
Paul Jakma | 923de65 | 2007-04-29 18:25:17 +0000 | [diff] [blame] | 177 | extern unsigned int attrhash_key_make (void *); |
paul | 94f2b39 | 2005-06-28 12:44:16 +0000 | [diff] [blame] | 178 | extern void attr_show_all (struct vty *); |
Paul Jakma | cbdfbaa | 2006-03-30 13:20:48 +0000 | [diff] [blame] | 179 | extern unsigned long int attr_count (void); |
| 180 | extern unsigned long int attr_unknown_count (void); |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 181 | |
| 182 | /* Cluster list prototypes. */ |
paul | 94f2b39 | 2005-06-28 12:44:16 +0000 | [diff] [blame] | 183 | extern int cluster_loop_check (struct cluster_list *, struct in_addr); |
| 184 | extern void cluster_unintern (struct cluster_list *); |
paul | 718e374 | 2002-12-13 20:15:29 +0000 | [diff] [blame] | 185 | |
| 186 | /* Transit attribute prototypes. */ |
| 187 | void transit_unintern (struct transit *); |
paul | 00d252c | 2005-05-23 14:19:54 +0000 | [diff] [blame] | 188 | |
Paul Jakma | 835315b | 2012-01-18 12:28:30 +0000 | [diff] [blame] | 189 | /* Below exported for unit-test purposes only */ |
| 190 | struct bgp_attr_parser_args { |
| 191 | struct peer *peer; |
| 192 | bgp_size_t length; /* attribute data length; */ |
| 193 | bgp_size_t total; /* total length, inc header */ |
| 194 | struct attr *attr; |
| 195 | u_int8_t type; |
| 196 | u_int8_t flags; |
| 197 | u_char *startp; |
| 198 | }; |
| 199 | extern int bgp_mp_reach_parse (struct bgp_attr_parser_args *args, |
| 200 | struct bgp_nlri *); |
| 201 | extern int bgp_mp_unreach_parse (struct bgp_attr_parser_args *args, |
| 202 | struct bgp_nlri *); |
Paul Jakma | 0329280 | 2008-06-07 20:37:10 +0000 | [diff] [blame] | 203 | |
Lou Berger | c374178 | 2016-01-12 13:42:01 -0500 | [diff] [blame] | 204 | extern struct bgp_attr_encap_subtlv * |
| 205 | encap_tlv_dup(struct bgp_attr_encap_subtlv *orig); |
| 206 | |
| 207 | extern void |
| 208 | bgp_attr_flush_encap(struct attr *attr); |
| 209 | |
Pradosh Mohapatra | 8c71e48 | 2014-01-15 06:57:57 +0000 | [diff] [blame] | 210 | /** |
| 211 | * Set of functions to encode MP_REACH_NLRI and MP_UNREACH_NLRI attributes. |
| 212 | * Typical call sequence is to call _start(), followed by multiple _prefix(), |
| 213 | * one for each NLRI that needs to be encoded into the UPDATE message, and |
| 214 | * finally the _end() function. |
| 215 | */ |
| 216 | extern size_t bgp_packet_mpattr_start(struct stream *s, afi_t afi, safi_t safi, |
| 217 | struct attr *attr); |
| 218 | extern void bgp_packet_mpattr_prefix(struct stream *s, afi_t afi, safi_t safi, |
| 219 | struct prefix *p, struct prefix_rd *prd, |
| 220 | u_char *tag); |
Lou Berger | 050defe | 2016-01-12 13:41:59 -0500 | [diff] [blame] | 221 | extern size_t bgp_packet_mpattr_prefix_size(afi_t afi, safi_t safi, |
| 222 | struct prefix *p); |
Pradosh Mohapatra | 8c71e48 | 2014-01-15 06:57:57 +0000 | [diff] [blame] | 223 | extern void bgp_packet_mpattr_end(struct stream *s, size_t sizep); |
| 224 | |
| 225 | extern size_t bgp_packet_mpunreach_start (struct stream *s, afi_t afi, |
| 226 | safi_t safi); |
| 227 | extern void bgp_packet_mpunreach_prefix (struct stream *s, struct prefix *p, |
| 228 | afi_t afi, safi_t safi, struct prefix_rd *prd, |
| 229 | u_char *tag); |
| 230 | extern void bgp_packet_mpunreach_end (struct stream *s, size_t attrlen_pnt); |
| 231 | |
paul | 00d252c | 2005-05-23 14:19:54 +0000 | [diff] [blame] | 232 | #endif /* _QUAGGA_BGP_ATTR_H */ |