Line data Source code
1 : /*
2 : * Copyright (c) 2013 Juniper Networks, Inc. All rights reserved.
3 : * Copyright Contributors to the OpenSDN project
4 : */
5 :
6 : #ifndef vnsw_inet_unicast_route_hpp
7 : #define vnsw_inet_unicast_route_hpp
8 :
9 : class VlanNhRoute;
10 : class LocalVmRoute;
11 : class InetInterfaceRoute;
12 : class ClonedLocalPath;
13 : class EcmpLoadBalance;
14 :
15 : //////////////////////////////////////////////////////////////////
16 : // UNICAST INET
17 : /////////////////////////////////////////////////////////////////
18 : class InetUnicastRouteKey : public AgentRouteKey {
19 : public:
20 10101 : InetUnicastRouteKey(const Peer *peer, const string &vrf_name,
21 10101 : const IpAddress &dip, uint8_t plen) :
22 10101 : AgentRouteKey(peer, vrf_name), dip_(dip), plen_(plen) { }
23 19404 : virtual ~InetUnicastRouteKey() { }
24 :
25 : //Called from oute creation in input of route table
26 : AgentRoute *AllocRouteEntry(VrfEntry *vrf, bool is_multicast) const;
27 10211 : virtual Agent::RouteTableType GetRouteTableType() {
28 10211 : if (dip_.is_v4()) {
29 7003 : return Agent::INET4_UNICAST;
30 : }
31 3208 : if (dip_.is_v6()) {
32 3208 : return Agent::INET6_UNICAST;
33 : }
34 0 : return Agent::INVALID;
35 : }
36 : virtual string ToString() const;
37 : virtual AgentRouteKey *Clone() const;
38 :
39 4981 : const IpAddress &addr() const {return dip_;}
40 0 : uint8_t plen() const {return plen_;}
41 :
42 : protected:
43 : IpAddress dip_;
44 : uint8_t plen_;
45 : private:
46 : DISALLOW_COPY_AND_ASSIGN(InetUnicastRouteKey);
47 : };
48 : class InetMplsUnicastRouteKey : public InetUnicastRouteKey {
49 : public:
50 44 : InetMplsUnicastRouteKey(const Peer *peer, const string &vrf_name,
51 44 : const IpAddress &dip, uint8_t plen) :
52 44 : InetUnicastRouteKey(peer, vrf_name, dip, plen) { }
53 88 : virtual ~InetMplsUnicastRouteKey() { }
54 :
55 27 : virtual Agent::RouteTableType GetRouteTableType() {
56 27 : if (dip_.is_v4()) {
57 27 : return Agent::INET4_MPLS;
58 : }
59 0 : return Agent::INVALID;
60 : }
61 : virtual AgentRouteKey *Clone() const;
62 :
63 : private:
64 : DISALLOW_COPY_AND_ASSIGN(InetMplsUnicastRouteKey);
65 : };
66 :
67 : class InetUnicastRouteEntry : public AgentRoute ,
68 : public AgentRoutePrefix<IpAddress> {
69 : public:
70 : InetUnicastRouteEntry(VrfEntry *vrf, const IpAddress &addr,
71 : uint8_t plen, bool is_multicast);
72 24758 : virtual ~InetUnicastRouteEntry() { }
73 :
74 : virtual int CompareTo(const Route &rhs) const;
75 : virtual std::string ToString() const;
76 : virtual KeyPtr GetDBRequestKey() const;
77 : virtual void SetKey(const DBRequestKey *key);
78 : virtual bool DBEntrySandesh(Sandesh *sresp, bool stale) const;
79 1520 : virtual const std::string GetAddressString() const {
80 1520 : return prefix_address_.to_string();
81 : }
82 0 : virtual const std::string GetSourceAddressString() const {
83 0 : return "0.0.0.0";
84 : }
85 : virtual Agent::RouteTableType GetTableType() const;
86 : virtual bool ReComputePathDeletion(AgentPath *path);
87 : virtual bool ReComputePathAdd(AgentPath *path);
88 : ///! @brief The length of Inet prefix IP address.
89 248393 : uint8_t prefix_length() const { return prefix_length_; }
90 0 : void set_addr(IpAddress addr) { prefix_address_ = addr; };
91 :
92 : //Key for patricia node lookup
93 : class Rtkey {
94 : public:
95 142990 : static std::size_t BitLength(const InetUnicastRouteEntry *key) {
96 142990 : return key->prefix_length();
97 : }
98 126598 : static char ByteValue(
99 : const InetUnicastRouteEntry *key, std::size_t i) {
100 126598 : if (key->prefix_address().is_v4()) {
101 : Ip4Address::bytes_type addr_bytes;
102 101554 : addr_bytes = key->prefix_address().to_v4().to_bytes();
103 101554 : char res = static_cast<char>(addr_bytes[i]);
104 101554 : return res;
105 : } else {
106 : Ip6Address::bytes_type addr_bytes;
107 25044 : addr_bytes = key->prefix_address().to_v6().to_bytes();
108 25044 : volatile char res = static_cast<char>(addr_bytes[i]);
109 25044 : return res;
110 : }
111 : }
112 : };
113 :
114 : bool DBEntrySandesh(Sandesh *sresp, IpAddress addr, uint8_t plen, bool stale) const;
115 : bool IsHostRoute() const;
116 : bool IpamSubnetRouteAvailable() const;
117 : InetUnicastRouteEntry *GetIpamSuperNetRoute() const;
118 :
119 : bool UpdateIpamHostFlags(bool ipam_host_route);
120 : bool UpdateRouteFlags(bool ipam_subnet_route, bool ipam_host_route,
121 : bool proxy_arp);
122 :
123 2915 : bool ipam_subnet_route() const {return ipam_subnet_route_;}
124 2426 : bool ipam_host_route() const { return ipam_host_route_; }
125 2448 : bool proxy_arp() const {return proxy_arp_;}
126 : virtual AgentPath *FindPathUsingKeyData(const AgentRouteKey *key,
127 : const AgentRouteData *data) const;
128 :
129 : protected:
130 : friend class InetUnicastAgentRouteTable;
131 :
132 : Patricia::Node rtnode_;
133 : // Flag set if route exactly matches a subnet in IPAM
134 : // ARP packets hitting this route must be flooded even if its ECMP route
135 : bool ipam_subnet_route_;
136 : // Flag set if this is host route and falls in an IPAM subnet
137 : // ARP packets hitting this route are flooded if MAC stitching is missing
138 : bool ipam_host_route_;
139 : // Specifies if ARP must be force proxied for this route
140 : bool proxy_arp_;
141 : private:
142 : AgentPath *FindEvpnPathUsingKeyData(const AgentRouteKey *key,
143 : const AgentRouteData *data) const;
144 : DISALLOW_COPY_AND_ASSIGN(InetUnicastRouteEntry);
145 : };
146 :
147 : class InetUnicastAgentRouteTable : public AgentRouteTable {
148 : public:
149 : typedef Patricia::Tree<InetUnicastRouteEntry,
150 : &InetUnicastRouteEntry::rtnode_,
151 : InetUnicastRouteEntry::Rtkey> InetRouteTree;
152 :
153 : InetUnicastAgentRouteTable(DB *db, const std::string &name);
154 444 : virtual ~InetUnicastAgentRouteTable() { }
155 :
156 : InetUnicastRouteEntry *FindLPM(const IpAddress &ip);
157 : InetUnicastRouteEntry *FindLPM(const InetUnicastRouteEntry &rt_key);
158 296 : virtual string GetTableName() const {
159 296 : if (type_ == Agent::INET4_UNICAST) {
160 148 : return "Inet4UnicastAgentRouteTable";
161 : }
162 148 : if (type_ == Agent::INET4_MPLS) {
163 0 : return "Inet4MplsAgentRouteTable";
164 : }
165 148 : if (type_ == Agent::INET6_UNICAST) {
166 148 : return "Inet6UnicastAgentRouteTable";
167 : }
168 0 : return "Unknown";
169 : }
170 17307 : virtual Agent::RouteTableType GetTableType() const {
171 17307 : return type_;
172 : }
173 938 : virtual void ProcessAdd(AgentRoute *rt) {
174 938 : tree_.Insert(static_cast<InetUnicastRouteEntry *>(rt));
175 938 : }
176 938 : virtual void ProcessDelete(AgentRoute *rt) {
177 938 : tree_.Remove(static_cast<InetUnicastRouteEntry *>(rt));
178 938 : }
179 : virtual AgentSandeshPtr GetAgentSandesh(const AgentSandeshArguments *args,
180 : const std::string &context);
181 58 : InetUnicastRouteEntry *FindRouteUsingKey(InetUnicastRouteEntry &key) {
182 58 : return FindLPM(key);
183 : }
184 111 : InetUnicastRouteEntry *FindRoute(const IpAddress &ip) {
185 111 : return FindLPM(ip);
186 : }
187 :
188 345 : const InetUnicastRouteEntry *GetNext(const InetUnicastRouteEntry *rt) {
189 345 : return static_cast<const InetUnicastRouteEntry *>(tree_.FindNext(rt));
190 : }
191 :
192 306 : InetUnicastRouteEntry *GetNextNonConst(const InetUnicastRouteEntry *rt) {
193 306 : return static_cast<InetUnicastRouteEntry *>(tree_.FindNext(rt));
194 : }
195 :
196 : static DBTableBase *CreateTable(DB *db, const std::string &name);
197 : static void DeleteReq(const Peer *peer, const string &vrf_name,
198 : const IpAddress &addr, uint8_t plen,
199 : AgentRouteData *data);
200 : static void DeleteMplsRouteReq(const Peer *peer, const string &vrf_name,
201 : const IpAddress &addr, uint8_t plen,
202 : AgentRouteData *data);
203 : static void Delete(const Peer *peer, const string &vrf_name,
204 : const IpAddress &addr, uint8_t plen);
205 : void Delete(const Peer *peer, const string &vrf_name,
206 : const IpAddress &addr, uint8_t plen,
207 : AgentRouteData *data);
208 : static void AddHostRoute(const string &vrf_name,
209 : const IpAddress &addr, uint8_t plen,
210 : const std::string &dest_vn_name,
211 : bool policy);
212 : void AddLocalVmRouteReq(const Peer *peer, const string &vm_vrf,
213 : const IpAddress &addr, uint8_t plen,
214 : LocalVmRoute *data);
215 : void AddLocalVmRouteReq(const Peer *peer, const string &vm_vrf,
216 : const IpAddress &addr, uint8_t plen,
217 : const boost::uuids::uuid &intf_uuid,
218 : const VnListType &vn_list,
219 : uint32_t label,
220 : const SecurityGroupList &sg_list,
221 : const TagList &tag_list,
222 : const CommunityList &communities,
223 : bool force_policy,
224 : const PathPreference &path_preference,
225 : const IpAddress &subnet_service_ip,
226 : const EcmpLoadBalance &ecmp_load_balance,
227 : bool is_local,
228 : bool is_health_check_service,
229 : bool native_encap,
230 : const std::string &intf_name = "",
231 : bool is_learnt_route = false);
232 : static void AddLocalVmRoute(const Peer *peer, const string &vm_vrf,
233 : const IpAddress &addr, uint8_t plen,
234 : const boost::uuids::uuid &intf_uuid,
235 : const VnListType &vn_list,
236 : uint32_t label,
237 : const SecurityGroupList &sg_list,
238 : const TagList &tag_list,
239 : const CommunityList &communities,
240 : bool force_policy,
241 : const PathPreference &path_preference,
242 : const IpAddress &subnet_service_ip,
243 : const EcmpLoadBalance &ecmp_load_balance,
244 : bool is_local, bool is_health_check_service,
245 : const std::string &intf_name,
246 : bool native_encap,
247 : const std::string &intf_route_type = VmInterface::kInterface,
248 : bool is_learnt_route = false);
249 : void ResyncRoute(const Peer *peer, const string &vrf,
250 : const IpAddress &addr, uint8_t plen);
251 : static void AddRemoteVmRouteReq(const Peer *peer, const string &vm_vrf,
252 : const IpAddress &vm_addr,uint8_t plen,
253 : AgentRouteData *data);
254 : void AddVlanNHRouteReq(const Peer *peer, const string &vm_vrf,
255 : const IpAddress &addr, uint8_t plen,
256 : VlanNhRoute *data);
257 : void AddVlanNHRouteReq(const Peer *peer, const string &vm_vrf,
258 : const IpAddress &addr, uint8_t plen,
259 : const boost::uuids::uuid &intf_uuid, uint16_t tag,
260 : uint32_t label, const VnListType &dest_vn_list,
261 : const SecurityGroupList &sg_list_,
262 : const TagList &tag_list,
263 : const PathPreference &path_preference);
264 : static void AddVlanNHRoute(const Peer *peer, const string &vm_vrf,
265 : const IpAddress &addr, uint8_t plen,
266 : const boost::uuids::uuid &intf_uuid, uint16_t tag,
267 : uint32_t label, const VnListType &dest_vn_list,
268 : const SecurityGroupList &sg_list_,
269 : const TagList &tag_list,
270 : const PathPreference &path_preference);
271 : InetUnicastRouteEntry *FindResolveRoute(const Ip4Address &ip);
272 : static InetUnicastRouteEntry *FindResolveRoute(const string &vrf_name,
273 : const Ip4Address &ip);
274 : static bool ShouldAddArp(const Ip4Address &ip);
275 : static void CheckAndAddArpReq(const string &vrf_name, const Ip4Address &ip,
276 : const Interface *intf,
277 : const VnListType &vn_list,
278 : const SecurityGroupList &sg,
279 : const TagList &tag);
280 : static void CheckAndAddArpRoute(const string &route_vrf_name,
281 : const Ip4Address &ip,
282 : const MacAddress &mac,
283 : const Interface *intf,
284 : bool resolved,
285 : const VnListType &vn_list,
286 : const SecurityGroupList &sg,
287 : const TagList &tag);
288 : static void AddArpReq(const string &route_vrf_name,
289 : const Ip4Address &ip,
290 : const string &nh_vrf_name,
291 : const Interface *intf,
292 : bool policy,
293 : const VnListType &dest_vn_list,
294 : const SecurityGroupList &sg_list,
295 : const TagList &tag_list);
296 : static void ArpRoute(DBRequest::DBOperation op,
297 : const string &route_vrf_name,
298 : const Ip4Address &ip,
299 : const MacAddress &mac,
300 : const string &nh_vrf_name,
301 : const Interface &intf,
302 : bool resolved,
303 : const uint8_t plen,
304 : bool policy,
305 : const VnListType &dest_vn_list,
306 : const SecurityGroupList &sg_list,
307 : const TagList &tag_list);
308 : static void NdpRoute(DBRequest::DBOperation op,
309 : const string &route_vrf_name,
310 : const IpAddress &ip,
311 : const MacAddress &mac,
312 : const string &nh_vrf_name,
313 : const Interface &intf,
314 : bool resolved,
315 : const uint8_t plen,
316 : bool policy,
317 : const VnListType &dest_vn_list,
318 : const SecurityGroupList &sg_list,
319 : const TagList &tag_list);
320 : static void AddResolveRoute(const Peer *peer,
321 : const string &vrf_name, const Ip4Address &ip,
322 : const uint8_t plen,
323 : const InterfaceKey &intf_key,
324 : const uint32_t label, bool policy,
325 : const std::string &vn_name,
326 : const SecurityGroupList &sg_list,
327 : const TagList &tag_list);
328 : void AddInetInterfaceRouteReq(const Peer *peer, const string &vm_vrf,
329 : const Ip4Address &addr, uint8_t plen,
330 : InetInterfaceRoute *data);
331 : void AddInetInterfaceRouteReq(const Peer *peer, const string &vm_vrf,
332 : const Ip4Address &addr, uint8_t plen,
333 : const string &interface,
334 : uint32_t label,
335 : const VnListType &vn_list);
336 :
337 : static void AddVHostRecvRoute(const Peer *peer, const string &vrf,
338 : const InterfaceKey &interface,
339 : const IpAddress &addr, uint8_t plen,
340 : const string &vn_name, bool policy,
341 : bool native_encap,
342 : bool ipam_host_route = true);
343 : static void AddVHostRecvRouteReq(const Peer *peer, const string &vrf,
344 : const InterfaceKey &interface,
345 : const IpAddress &addr, uint8_t plen,
346 : const string &vn_name, bool policy,
347 : bool native_encap);
348 : static void AddVHostMplsRecvRouteReq(const Peer *peer, const string &vrf,
349 : const InterfaceKey &interface,
350 : const IpAddress &addr, uint8_t plen,
351 : const string &vn_name, bool policy,
352 : bool native_encap);
353 : static void AddVHostSubnetRecvRoute(const Peer *peer, const string &vrf,
354 : const InterfaceKey &interface,
355 : const Ip4Address &addr, uint8_t plen,
356 : const std::string &vn_name,
357 : bool policy);
358 : static void DelVHostSubnetRecvRoute(const string &vm_vrf,
359 : const Ip4Address &addr, uint8_t plen);
360 : static void AddDropRoute(const string &vm_vrf,
361 : const Ip4Address &addr, uint8_t plen,
362 : const string &vn_name);
363 : static void AddGatewayRoute(const Peer *peer,
364 : const string &vrf_name,
365 : const Ip4Address &dst_addr,uint8_t plen,
366 : const AddressList &gw_list,
367 : const VnListType &vn_name, uint32_t label,
368 : const SecurityGroupList &sg_list,
369 : const TagList &tag_list,
370 : const CommunityList &communities,
371 : bool native_encap);
372 : static void AddGatewayRouteReq(const Peer *peer,
373 : const string &vrf_name,
374 : const Ip4Address &dst_addr,uint8_t plen,
375 : const AddressList &gw_list,
376 : const VnListType &vn_name, uint32_t label,
377 : const SecurityGroupList &sg_list,
378 : const TagList &tag_list,
379 : const CommunityList &communities,
380 : bool native_encap);
381 : static void AddLocalMplsRouteReq(const Peer *peer,
382 : const string &vrf_name,
383 : const Ip4Address &dst_addr,uint8_t plen,
384 : const Ip4Address &gw_ip,
385 : const VnListType &vn_name, uint32_t label,
386 : const SecurityGroupList &sg_list,
387 : const TagList &tag_list,
388 : const CommunityList &communities,
389 : bool native_encap);
390 : static void AddMplsRouteInternal(const Peer *peer,
391 : DBRequest *req, const string &vrf_name,
392 : const IpAddress &dst_addr, uint8_t plen,
393 : const IpAddress &gw_ip,
394 : const VnListType &vn_name, uint32_t label,
395 : const SecurityGroupList &sg_list,
396 : const TagList &tag_list,
397 : const CommunityList &communities,
398 : bool native_encap);
399 : static void AddMplsRouteReq(const Peer *peer,
400 : const string &vrf_name,
401 : const IpAddress &dst_addr,uint8_t plen,
402 : AgentRouteData *data);
403 : void AddIpamSubnetRoute(const string &vm_vrf, const IpAddress &addr,
404 : uint8_t plen, const std::string &vn_name);
405 : void AddVrouterSubnetRoute(const IpAddress &dst_addr, uint8_t plen);
406 : void AddVhostMplsRoute(const IpAddress &vhost_addr, const Peer *peer);
407 : void AddInterfaceRouteReq(Agent *agent, const Peer *peer,
408 : const string &vrf_name,
409 : const Ip4Address &ip, uint8_t plen,
410 : const Interface *intrface,
411 : const std::string &vn_name);
412 : void AddClonedLocalPathReq(const Peer *peer, const string &vm_vrf,
413 : const IpAddress &addr,
414 : uint8_t plen, ClonedLocalPath *data);
415 : bool ResyncSubnetRoutes(const InetUnicastRouteEntry *rt, bool val);
416 : uint8_t GetHostPlen(const IpAddress &ip_addr) const;
417 : void AddEvpnRoute(const AgentRoute *evpn_entry);
418 : void DeleteEvpnRoute(const AgentRoute *rt);
419 : void TraverseHostRoutesInSubnet(InetUnicastRouteEntry *rt,
420 : const Peer *peer);
421 : IpAddress GetSubnetAddress(const IpAddress &addr,
422 : uint16_t plen) const;
423 : InetUnicastRouteEntry *GetSuperNetRoute(const IpAddress &addr);
424 : void AddEvpnRoutingRoute(const IpAddress &ip_addr,
425 : uint8_t plen,
426 : const VrfEntry *vrf,
427 : const Peer *peer,
428 : const SecurityGroupList &sg_list,
429 : const CommunityList &communities,
430 : const PathPreference &path_preference,
431 : const EcmpLoadBalance &ecmp_load_balance,
432 : const TagList &tag_list,
433 : DBRequest &nh_req,
434 : uint32_t vxlan_id,
435 : const VnListType& vn_list,
436 : const std::string& origin_vn = "");
437 : void AddEvpnRoutingRouteReq(const IpAddress &ip_addr,
438 : uint8_t plen,
439 : const VrfEntry *vrf,
440 : const Peer *peer,
441 : const SecurityGroupList &sg_list,
442 : const CommunityList &communities,
443 : const PathPreference &path_preference,
444 : const EcmpLoadBalance &ecmp_load_balance,
445 : const TagList &tag_list,
446 : DBRequest &nh_req,
447 : uint32_t vxlan_id,
448 : const VnListType& vn_list,
449 : const std::string& origin_vn = "");
450 :
451 :
452 : private:
453 : Agent::RouteTableType type_;
454 : InetRouteTree tree_;
455 : Patricia::Node rtnode_;
456 : DBTableWalker::WalkId walkid_;
457 : DISALLOW_COPY_AND_ASSIGN(InetUnicastAgentRouteTable);
458 : };
459 :
460 : #endif // vnsw_inet_unicast_route_hpp
|