diff options
author | Sridhar Samudrala <sridhar.samudrala@intel.com> | 2015-09-02 16:12:23 -0700 |
---|---|---|
committer | Jiri Pirko <jiri@resnulli.us> | 2015-09-03 07:37:35 +0200 |
commit | beb831fdc19195aecb365c4b48b6d8451c59251c (patch) | |
tree | 073b02dd449c92450d0177de39667d92d12df3b2 | |
parent | 2a0f604b5152a7abf0503c731c24ad29cd3c0cf9 (diff) | |
download | libteam-beb831fdc19195aecb365c4b48b6d8451c59251c.tar.gz |
teamd: lacp: Don't send LACP frames when master team device is down.
Watch for team admin state changes and update the member ports state
to enable/disable sending LACP frames.
Signed-off-by: Sridhar Samudrala <sridhar.samudrala@intel.com>
Signed-off-by: Jiri Pirko <jiri@resnulli.us>
-rw-r--r-- | teamd/teamd_runner_lacp.c | 35 |
1 files changed, 31 insertions, 4 deletions
diff --git a/teamd/teamd_runner_lacp.c b/teamd/teamd_runner_lacp.c index 59d505d..09899ce 100644 --- a/teamd/teamd_runner_lacp.c +++ b/teamd/teamd_runner_lacp.c @@ -1016,6 +1016,11 @@ static int lacpdu_send(struct lacp_port *lacp_port) struct sockaddr_ll ll_my; struct sockaddr_ll ll_slow; int err; + bool admin_state; + + admin_state = team_get_ifinfo_admin_state(lacp_port->ctx->ifinfo); + if (!admin_state) + return 0; err = teamd_getsockname_hwaddr(lacp_port->sock, &ll_my, 0); if (err) @@ -1302,6 +1307,27 @@ static int lacp_event_watch_hwaddr_changed(struct teamd_context *ctx, return 0; } +static int lacp_event_watch_admin_state_changed(struct teamd_context *ctx, + void *priv) +{ + struct lacp *lacp = priv; + struct teamd_port *tdport; + bool admin_state; + int err; + + teamd_for_each_tdport(tdport, ctx) { + struct lacp_port *lacp_port = lacp_port_get(lacp, tdport); + + admin_state = team_get_ifinfo_admin_state(ctx->ifinfo); + err = lacp_port_set_state(lacp_port, + admin_state?PORT_STATE_CURRENT:PORT_STATE_DISABLED); + if (err) + return err; + } + return 0; +} + + static int lacp_event_watch_port_added(struct teamd_context *ctx, struct teamd_port *tdport, void *priv) { @@ -1331,11 +1357,12 @@ static int lacp_event_watch_port_changed(struct teamd_context *ctx, return lacp_port_link_update(lacp_port); } -static const struct teamd_event_watch_ops lacp_port_watch_ops = { +static const struct teamd_event_watch_ops lacp_event_watch_ops = { .hwaddr_changed = lacp_event_watch_hwaddr_changed, .port_added = lacp_event_watch_port_added, .port_removed = lacp_event_watch_port_removed, .port_changed = lacp_event_watch_port_changed, + .admin_state_changed = lacp_event_watch_admin_state_changed, }; static int lacp_carrier_init(struct teamd_context *ctx, struct lacp *lacp) @@ -1816,7 +1843,7 @@ static int lacp_init(struct teamd_context *ctx, void *priv) teamd_log_err("Failed to initialize carrier."); return err; } - err = teamd_event_watch_register(ctx, &lacp_port_watch_ops, lacp); + err = teamd_event_watch_register(ctx, &lacp_event_watch_ops, lacp); if (err) { teamd_log_err("Failed to register event watch."); return err; @@ -1836,7 +1863,7 @@ static int lacp_init(struct teamd_context *ctx, void *priv) balancer_fini: teamd_balancer_fini(lacp->tb); event_watch_unregister: - teamd_event_watch_unregister(ctx, &lacp_port_watch_ops, lacp); + teamd_event_watch_unregister(ctx, &lacp_event_watch_ops, lacp); return err; } @@ -1846,7 +1873,7 @@ static void lacp_fini(struct teamd_context *ctx, void *priv) teamd_state_val_unregister(ctx, &lacp_state_vg, lacp); teamd_balancer_fini(lacp->tb); - teamd_event_watch_unregister(ctx, &lacp_port_watch_ops, lacp); + teamd_event_watch_unregister(ctx, &lacp_event_watch_ops, lacp); lacp_carrier_fini(ctx, lacp); } |