Skip to content

Commit

Permalink
Merge "ECMP load balance configuration agent changes."
Browse files Browse the repository at this point in the history
  • Loading branch information
Zuul authored and opencontrail-ci-admin committed Jan 18, 2016
2 parents 9a3b188 + f6dd3dc commit ae3ea2f
Show file tree
Hide file tree
Showing 29 changed files with 585 additions and 81 deletions.
14 changes: 8 additions & 6 deletions src/schema/vnc_cfg.xsd
Expand Up @@ -807,9 +807,6 @@ targetNamespace="http://www.contrailsystems.com/2012/VNC-CONFIG/0">
<xsd:element name='forwarding-mode' type='ForwardingModeType'/>
<!-- Enable or disable unicast RPF for virtual-network -->
<xsd:element name='rpf' type='RpfModeType'/>
<!-- Ecmp nexthop load balance criterias -->
<xsd:element name='ecmp-hashing-include-fields'
type='EcmpHashingIncludeFields'/>
</xsd:all>
</xsd:complexType>

Expand All @@ -833,6 +830,10 @@ targetNamespace="http://www.contrailsystems.com/2012/VNC-CONFIG/0">
<!--#IFMAP-SEMANTICS-IDL
Property('virtual-network-properties', 'virtual-network') -->

<!-- Ecmp nexthop load balance criterias -->
<!--#IFMAP-SEMANTICS-IDL
Property('ecmp-hashing-include-fields', 'virtual-network') -->

<xsd:element name="provider-properties" type="ProviderDetails"/>
<!--#IFMAP-SEMANTICS-IDL
Property('provider-properties', 'virtual-network') -->
Expand Down Expand Up @@ -1054,9 +1055,6 @@ targetNamespace="http://www.contrailsystems.com/2012/VNC-CONFIG/0">
<xsd:element name='interface-mirror' type="InterfaceMirrorType"/>
<xsd:element name="local-preference" type="xsd:integer"/>
<xsd:element name="sub-interface-vlan-tag" type="xsd:integer"/>
<!-- Ecmp nexthop load balance criterias -->
<xsd:element name='ecmp-hashing-include-fields'
type='EcmpHashingIncludeFields'/>
</xsd:all>
</xsd:complexType>

Expand All @@ -1077,6 +1075,10 @@ targetNamespace="http://www.contrailsystems.com/2012/VNC-CONFIG/0">
</xsd:all>
</xsd:complexType>

<!-- Ecmp nexthop load balance criterias -->
<!--#IFMAP-SEMANTICS-IDL
Property('ecmp-hashing-include-fields', 'virtual-machine-interface') -->

<xsd:element name="virtual-machine-interface-properties"
type="VirtualMachineInterfacePropertiesType"/>
<!--#IFMAP-SEMANTICS-IDL
Expand Down
10 changes: 8 additions & 2 deletions src/vnsw/agent/controller/controller_export.cc
Expand Up @@ -5,6 +5,7 @@
#include <boost/uuid/uuid_io.hpp>

#include <cmn/agent_cmn.h>
#include <oper/ecmp_load_balance.h>
#include <oper/route_common.h>
#include <oper/peer.h>
#include <oper/nexthop.h>
Expand All @@ -22,7 +23,7 @@ RouteExport::State::State() :
DBState(), exported_(false), fabric_multicast_exported_(false),
force_chg_(false), label_(MplsTable::kInvalidLabel), vn_(), sg_list_(),
tunnel_type_(TunnelType::INVALID), path_preference_(),
destination_(), source_() {
destination_(), source_(), ecmp_load_balance_() {
}

bool RouteExport::State::Changed(const AgentRoute *route, const AgentPath *path) const {
Expand Down Expand Up @@ -51,6 +52,9 @@ bool RouteExport::State::Changed(const AgentRoute *route, const AgentPath *path)
if (path_preference_ != path->path_preference())
return true;

if(ecmp_load_balance_ != path->ecmp_load_balance())
return true;

return false;
}

Expand All @@ -62,6 +66,7 @@ void RouteExport::State::Update(const AgentRoute *route, const AgentPath *path)
communities_ = path->communities();
tunnel_type_ = path->tunnel_type();
path_preference_ = path->path_preference();
ecmp_load_balance_ = path->ecmp_load_balance();
}

RouteExport::RouteExport(AgentRouteTable *rt_table):
Expand Down Expand Up @@ -180,7 +185,8 @@ void RouteExport::UnicastNotify(AgentXmppChannel *bgp_xmpp_peer,
path->NexthopIp(table->agent()), vn_list,
state->label_, path->GetTunnelBmap(),
&path->sg_list(), &path->communities(),
type, state->path_preference_);
type, state->path_preference_,
state->ecmp_load_balance_);
}
} else {
if (state->exported_ == true) {
Expand Down
2 changes: 2 additions & 0 deletions src/vnsw/agent/controller/controller_export.h
Expand Up @@ -12,6 +12,7 @@
#include <oper/agent_path.h>

class AgentPath;
class EcmpLoadBalance;

class RouteExport {
public:
Expand All @@ -32,6 +33,7 @@ class RouteExport {
//destination and source are valid for tunnel NH.
std::string destination_;
std::string source_;
EcmpLoadBalance ecmp_load_balance_;

bool Changed(const AgentRoute *route, const AgentPath *path) const;
void Update(const AgentRoute *route, const AgentPath *path);
Expand Down
70 changes: 64 additions & 6 deletions src/vnsw/agent/controller/controller_peer.cc
Expand Up @@ -22,6 +22,7 @@
#include "oper/peer.h"
#include "oper/vxlan.h"
#include "oper/agent_path.h"
#include "oper/ecmp_load_balance.h"
#include "cmn/agent_stats.h"
#include <pugixml/pugixml.hpp>
#include "xml/xml_pugi.h"
Expand Down Expand Up @@ -604,9 +605,45 @@ void AgentXmppChannel::ReceiveV4V6Update(XmlPugi *pugi) {
}
}

static void GetEcmpHashFieldsToUse(ItemType *item,
EcmpLoadBalance &ecmp_load_balance) {
if (item->entry.load_balance.load_balance_decision.empty() ||
item->entry.load_balance.load_balance_decision !=
LoadBalanceDecision)
ecmp_load_balance.SetAll();

uint8_t field_list_size = item->entry.
load_balance.load_balance_fields.load_balance_field_list.size();
if (field_list_size == 0)
ecmp_load_balance.SetAll();

for (uint32_t i = 0; i < field_list_size; i++) {
std::string field_type = item->entry.
load_balance.load_balance_fields.load_balance_field_list[i];
if (field_type == ecmp_load_balance.source_mac_str())
ecmp_load_balance.set_source_mac();
if (field_type == ecmp_load_balance.destination_mac_str())
ecmp_load_balance.set_destination_mac();
if (field_type == ecmp_load_balance.source_ip_str())
ecmp_load_balance.set_source_ip();
if (field_type == ecmp_load_balance.destination_ip_str())
ecmp_load_balance.set_destination_ip();
if (field_type == ecmp_load_balance.ip_protocol_str())
ecmp_load_balance.set_ip_protocol();
if (field_type == ecmp_load_balance.source_port_str())
ecmp_load_balance.set_source_port();
if (field_type == ecmp_load_balance.destination_port_str())
ecmp_load_balance.set_destination_port();
}
}

void AgentXmppChannel::AddEcmpRoute(string vrf_name, IpAddress prefix_addr,
uint32_t prefix_len, ItemType *item,
const VnListType &vn_list) {
//Extract the load balancer fields.
EcmpLoadBalance ecmp_load_balance;
GetEcmpHashFieldsToUse(item, ecmp_load_balance);

PathPreference::Preference preference = PathPreference::LOW;
TunnelType::TypeBmap encap = TunnelType::MplsType(); //default
if (item->entry.local_preference == PathPreference::HIGH) {
Expand Down Expand Up @@ -690,7 +727,7 @@ void AgentXmppChannel::AddEcmpRoute(string vrf_name, IpAddress prefix_addr,
new ControllerEcmpRoute(bgp_peer_id(), prefix_addr, prefix_len,
vn_list, -1, false, vrf_name,
item->entry.security_group_list.security_group,
rp, encap, nh_req);
rp, encap, ecmp_load_balance, nh_req);

//ECMP create component NH
rt_table->AddRemoteVmRouteReq(bgp_peer_id(), vrf_name,
Expand Down Expand Up @@ -902,6 +939,8 @@ void AgentXmppChannel::AddEvpnRoute(const std::string &vrf_name,
ControllerLocalVmRoute *local_vm_route = NULL;
VnListType vn_list;
vn_list.insert(item->entry.virtual_network);
EcmpLoadBalance ecmp_load_balance;

if (encap == TunnelType::VxlanType()) {
local_vm_route =
new ControllerLocalVmRoute(intf_key,
Expand All @@ -910,6 +949,7 @@ void AgentXmppChannel::AddEvpnRoute(const std::string &vrf_name,
InterfaceNHFlags::BRIDGE,
sg_list, path_preference,
unicast_sequence_number(),
ecmp_load_balance,
this);
} else {
local_vm_route =
Expand All @@ -920,6 +960,7 @@ void AgentXmppChannel::AddEvpnRoute(const std::string &vrf_name,
InterfaceNHFlags::BRIDGE,
sg_list, path_preference,
unicast_sequence_number(),
ecmp_load_balance,
this);
}
rt_table->AddLocalVmRouteReq(bgp_peer_id(), vrf_name, mac,
Expand Down Expand Up @@ -990,6 +1031,7 @@ void AgentXmppChannel::AddRemoteRoute(string vrf_name, IpAddress prefix_addr,

VmInterfaceKey intf_key(AgentKey::ADD_DEL_CHANGE,
intf_nh->GetIfUuid(), "");
EcmpLoadBalance ecmp_load_balance;
BgpPeer *bgp_peer = bgp_peer_id();
if (interface->type() == Interface::VM_INTERFACE) {
ControllerLocalVmRoute *local_vm_route =
Expand All @@ -1000,6 +1042,7 @@ void AgentXmppChannel::AddRemoteRoute(string vrf_name, IpAddress prefix_addr,
item->entry.security_group_list.security_group,
path_preference,
unicast_sequence_number(),
ecmp_load_balance,
this);
rt_table->AddLocalVmRouteReq(bgp_peer, vrf_name,
prefix_addr, prefix_len,
Expand Down Expand Up @@ -1750,6 +1793,17 @@ bool AgentXmppChannel::ControllerSendSubscribe(AgentXmppChannel *peer,
return true;
}

void PopulateEcmpHashFieldsToUse(ItemType &item,
const EcmpLoadBalance &ecmp_load_balance) {
item.entry.load_balance.load_balance_decision = LoadBalanceDecision;

if (ecmp_load_balance.AllSet())
return;

ecmp_load_balance.GetStringVector(
item.entry.load_balance.load_balance_fields.load_balance_field_list);
}

bool AgentXmppChannel::ControllerSendV4V6UnicastRouteCommon(AgentRoute *route,
const VnListType &vn_list,
const SecurityGroupList *sg_list,
Expand All @@ -1758,7 +1812,8 @@ bool AgentXmppChannel::ControllerSendV4V6UnicastRouteCommon(AgentRoute *route,
TunnelType::TypeBmap bmap,
const PathPreference &path_preference,
bool associate,
Agent::RouteTableType type) {
Agent::RouteTableType type,
const EcmpLoadBalance &ecmp_load_balance) {

static int id = 0;
ItemType item;
Expand All @@ -1781,6 +1836,7 @@ bool AgentXmppChannel::ControllerSendV4V6UnicastRouteCommon(AgentRoute *route,

string rtr(agent_->router_id().to_string());

PopulateEcmpHashFieldsToUse(item, ecmp_load_balance);
autogen::NextHopType nh;
nh.af = BgpAf::IPv4;
nh.address = rtr;
Expand Down Expand Up @@ -2412,8 +2468,8 @@ bool AgentXmppChannel::ControllerSendRouteAdd(AgentXmppChannel *peer,
const SecurityGroupList *sg_list,
const CommunityList *communities,
Agent::RouteTableType type,
const PathPreference
&path_preference)
const PathPreference &path_preference,
const EcmpLoadBalance &ecmp_load_balance)
{
if (!peer) return false;

Expand All @@ -2428,7 +2484,7 @@ bool AgentXmppChannel::ControllerSendRouteAdd(AgentXmppChannel *peer,
ret = peer->ControllerSendV4V6UnicastRouteCommon(route, vn_list,
sg_list, communities, label,
bmap, path_preference, true,
type);
type, ecmp_load_balance);
}
if (type == Agent::EVPN) {
std::string vn = *vn_list.begin();
Expand Down Expand Up @@ -2461,13 +2517,15 @@ bool AgentXmppChannel::ControllerSendRouteDelete(AgentXmppChannel *peer,
bool ret = false;
if (((type == Agent::INET4_UNICAST) || (type == Agent::INET6_UNICAST)) &&
(peer->agent()->simulate_evpn_tor() == false)) {
EcmpLoadBalance ecmp_load_balance;
ret = peer->ControllerSendV4V6UnicastRouteCommon(route, vn_list,
sg_list, communities,
label,
bmap,
path_preference,
false,
type);
type,
ecmp_load_balance);
}
if (type == Agent::EVPN) {
Ip4Address nh_ip(0);
Expand Down
7 changes: 5 additions & 2 deletions src/vnsw/agent/controller/controller_peer.h
Expand Up @@ -24,6 +24,7 @@ class VrfEntry;
class XmlPugi;
class PathPreference;
class AgentPath;
class EcmpLoadBalance;

class AgentXmppChannel {
public:
Expand Down Expand Up @@ -73,7 +74,8 @@ class AgentXmppChannel {
const SecurityGroupList *sg_list,
const CommunityList *communities,
Agent::RouteTableType type,
const PathPreference &path_preference);
const PathPreference &path_preference,
const EcmpLoadBalance &ecmp_load_balance);
static bool ControllerSendEvpnRouteAdd(AgentXmppChannel *peer,
AgentRoute *route,
const Ip4Address *nexthop_ip,
Expand Down Expand Up @@ -189,7 +191,8 @@ class AgentXmppChannel {
uint32_t tunnel_bmap,
const PathPreference &path_preference,
bool associate,
Agent::RouteTableType type);
Agent::RouteTableType type,
const EcmpLoadBalance &ecmp_load_balance);
bool BuildTorMulticastMessage(autogen::EnetItemType &item,
std::stringstream &node_id,
AgentRoute *route,
Expand Down
5 changes: 4 additions & 1 deletion src/vnsw/agent/controller/controller_route_path.cc
Expand Up @@ -9,6 +9,7 @@
#include <route/route.h>

#include <cmn/agent_cmn.h>
#include <oper/ecmp_load_balance.h>
#include <oper/route_common.h>
#include <oper/vrf.h>
#include <oper/tunnel_nh.h>
Expand Down Expand Up @@ -72,6 +73,7 @@ bool ControllerEcmpRoute::AddChangePath(Agent *agent, AgentPath *path,
vrf_name_, sg_list_,
path_preference_,
tunnel_bmap_,
ecmp_load_balance_,
nh_req_, agent, path);
}

Expand Down Expand Up @@ -249,10 +251,11 @@ ControllerLocalVmRoute::ControllerLocalVmRoute(const VmInterfaceKey &intf,
const SecurityGroupList &sg_list,
const PathPreference &path_preference,
uint64_t sequence_number,
const EcmpLoadBalance &ecmp_load_balance,
const AgentXmppChannel *channel) :
LocalVmRoute(intf, mpls_label, vxlan_id, force_policy, vn_list, flags, sg_list,
CommunityList(),
path_preference, Ip4Address(0)),
path_preference, Ip4Address(0), ecmp_load_balance),
sequence_number_(sequence_number), channel_(channel) { }

bool ControllerLocalVmRoute::IsPeerValid(const AgentRouteKey *key) const {
Expand Down
7 changes: 6 additions & 1 deletion src/vnsw/agent/controller/controller_route_path.h
Expand Up @@ -12,6 +12,7 @@
//Forward declaration
class AgentXmppChannel;
class AgentRouteData;
class EcmpLoadBalance;
class Peer;
class BgpPeer;
class TunnelNHKey;
Expand Down Expand Up @@ -127,11 +128,13 @@ class ControllerEcmpRoute : public ControllerPeerPath {
const string &vrf_name, SecurityGroupList sg_list,
const PathPreference &path_preference,
TunnelType::TypeBmap tunnel_bmap,
const EcmpLoadBalance &ecmp_load_balance,
DBRequest &nh_req) :
ControllerPeerPath(peer), dest_addr_(dest_addr), plen_(plen),
vn_list_(vn_list), label_(label), local_ecmp_nh_(local_ecmp_nh),
vrf_name_(vrf_name), sg_list_(sg_list),
path_preference_(path_preference), tunnel_bmap_(tunnel_bmap)
path_preference_(path_preference), tunnel_bmap_(tunnel_bmap),
ecmp_load_balance_(ecmp_load_balance)
{nh_req_.Swap(&nh_req);}

virtual ~ControllerEcmpRoute() { }
Expand All @@ -150,6 +153,7 @@ class ControllerEcmpRoute : public ControllerPeerPath {
SecurityGroupList sg_list_;
PathPreference path_preference_;
TunnelType::TypeBmap tunnel_bmap_;
EcmpLoadBalance ecmp_load_balance_;
DBRequest nh_req_;
DISALLOW_COPY_AND_ASSIGN(ControllerEcmpRoute);
};
Expand All @@ -167,6 +171,7 @@ class ControllerLocalVmRoute : public LocalVmRoute {
const SecurityGroupList &sg_list,
const PathPreference &path_preference,
uint64_t sequence_number,
const EcmpLoadBalance &ecmp_load_balance,
const AgentXmppChannel *channel);
virtual ~ControllerLocalVmRoute() { }
virtual bool IsPeerValid(const AgentRouteKey *key) const;
Expand Down
5 changes: 4 additions & 1 deletion src/vnsw/agent/openstack/instance_service_server.cc
Expand Up @@ -26,6 +26,7 @@
#include <oper/vm.h>
#include <oper/vn.h>
#include <oper/mirror_table.h>
#include <oper/ecmp_load_balance.h>
#include <cfg/cfg_types.h>
#include <openstack/instance_service_server.h>
#include <base/contrail_ports.h>
Expand Down Expand Up @@ -422,11 +423,13 @@ InstanceServiceAsyncHandler::AddLocalVmRoute(const std::string& ip_address,

VnListType vn_list;
vn_list.insert("instance-service");
EcmpLoadBalance ecmp_load_balance;
agent_->fabric_inet4_unicast_table()->
AddLocalVmRouteReq(novaPeer_.get(), vrf, ip.to_v4(), 32, intf_uuid,
vn_list, mpls_label, SecurityGroupList(),
CommunityList(),
false, PathPreference(), Ip4Address(0));
false, PathPreference(), Ip4Address(0),
ecmp_load_balance);
return true;
}

Expand Down

0 comments on commit ae3ea2f

Please sign in to comment.