dpif_port = NULL;
}
if (iface) {
+ if (iface->port->bond) {
+ /* The bond has a pointer to the netdev, so remove it
+ * from the bond before closing the netdev. The slave
+ * will get added back to the bond later, after a new
+ * netdev is available. */
+ bond_slave_unregister(iface->port->bond, iface);
+ }
netdev_close(iface->netdev);
iface->netdev = NULL;
}
port->cfg = cfg;
-
/* Add new interfaces and update 'cfg' member of existing ones. */
sset_init(&new_ifaces);
for (i = 0; i < cfg->n_interfaces; i++) {
const struct ovsrec_interface *if_cfg = cfg->interfaces[i];
struct iface *iface;
+ const char *type;
if (!sset_add(&new_ifaces, if_cfg->name)) {
VLOG_WARN("port %s: %s specified twice as port interface",
continue;
}
+ /* Determine interface type. The local port always has type
+ * "internal". Other ports take their type from the database and
+ * default to "system" if none is specified. */
+ type = (!strcmp(if_cfg->name, port->bridge->name) ? "internal"
+ : if_cfg->type[0] ? if_cfg->type
+ : "system");
+
iface = iface_lookup(port->bridge, if_cfg->name);
- if (iface) {
+ if (!strcmp(type, "null")) {
+ iface_destroy(iface);
+ continue;
+ } else if (iface) {
if (iface->port != port) {
VLOG_ERR("bridge %s: %s interface is on multiple ports, "
"removing from %s",
iface = iface_create(port, if_cfg);
}
- /* Determine interface type. The local port always has type
- * "internal". Other ports take their type from the database and
- * default to "system" if none is specified. */
- iface->type = (!strcmp(if_cfg->name, port->bridge->name) ? "internal"
- : if_cfg->type[0] ? if_cfg->type
- : "system");
+ iface->type = type;
}
sset_destroy(&new_ifaces);
iface_reconfigure_lacp(struct iface *iface)
{
struct lacp_slave_settings s;
- int priority, portid;
+ int priority, portid, key;
portid = atoi(get_interface_other_config(iface->cfg, "lacp-port-id", "0"));
priority = atoi(get_interface_other_config(iface->cfg,
"lacp-port-priority", "0"));
+ key = atoi(get_interface_other_config(iface->cfg, "lacp-aggregation-key",
+ "0"));
if (portid <= 0 || portid > UINT16_MAX) {
portid = iface->dp_ifidx;
priority = UINT16_MAX;
}
+ if (key < 0 || key > UINT16_MAX) {
+ key = 0;
+ }
+
s.name = iface->name;
s.id = portid;
s.priority = priority;
+ s.key = key;
lacp_slave_register(iface->port->lacp, iface, &s);
}
? priority
: UINT16_MAX - !list_is_short(&port->ifaces));
- s.strict = !strcmp(get_port_other_config(port->cfg, "lacp-strict",
- "false"),
- "true");
+ s.heartbeat = !strcmp(get_port_other_config(port->cfg,
+ "lacp-heartbeat",
+ "false"), "true");
lacp_time = get_port_other_config(port->cfg, "lacp-time", "slow");
custom_time = atoi(lacp_time);
s.up_delay = MAX(0, port->cfg->bond_updelay);
s.down_delay = MAX(0, port->cfg->bond_downdelay);
+ s.basis = atoi(get_port_other_config(port->cfg, "bond-hash-basis", "0"));
+
s.rebalance_interval = atoi(
get_port_other_config(port->cfg, "bond-rebalance-interval", "10000"));
if (s.rebalance_interval < 1000) {
}
LIST_FOR_EACH (iface, port_elem, &port->ifaces) {
- uint16_t stable_id = (port->lacp
- ? lacp_slave_get_port_id(port->lacp, iface)
- : iface->dp_ifidx);
+ long long stable_id;
+
+ stable_id = atoll(get_interface_other_config(iface->cfg,
+ "bond-stable-id", "0"));
+
+ if (stable_id <= 0 || stable_id >= UINT32_MAX) {
+ stable_id = odp_port_to_ofp_port(iface->dp_ifidx);
+ }
+
bond_slave_register(iface->port->bond, iface, stable_id,
iface->netdev);
}