diff options
Diffstat (limited to 'drivers/net/bonding/bond_options.c')
-rw-r--r-- | drivers/net/bonding/bond_options.c | 30 |
1 files changed, 23 insertions, 7 deletions
diff --git a/drivers/net/bonding/bond_options.c b/drivers/net/bonding/bond_options.c index 18b1cc0d8b8..2315104de8c 100644 --- a/drivers/net/bonding/bond_options.c +++ b/drivers/net/bonding/bond_options.c @@ -244,6 +244,16 @@ static struct bond_option bond_opts[] = { .values = bond_use_carrier_tbl, .set = bond_option_use_carrier_set }, + [BOND_OPT_ACTIVE_SLAVE] = { + .id = BOND_OPT_ACTIVE_SLAVE, + .name = "active_slave", + .desc = "Currently active slave", + .flags = BOND_OPTFLAG_RAWVAL, + .unsuppmodes = BOND_MODE_ALL_EX(BIT(BOND_MODE_ACTIVEBACKUP) | + BIT(BOND_MODE_TLB) | + BIT(BOND_MODE_ALB)), + .set = bond_option_active_slave_set + }, { } }; @@ -556,10 +566,21 @@ struct net_device *bond_option_active_slave_get(struct bonding *bond) } int bond_option_active_slave_set(struct bonding *bond, - struct net_device *slave_dev) + struct bond_opt_value *newval) { + char ifname[IFNAMSIZ] = { 0, }; + struct net_device *slave_dev; int ret = 0; + sscanf(newval->string, "%15s", ifname); /* IFNAMSIZ */ + if (!strlen(ifname) || newval->string[0] == '\n') { + slave_dev = NULL; + } else { + slave_dev = __dev_get_by_name(dev_net(bond->dev), ifname); + if (!slave_dev) + return -ENODEV; + } + if (slave_dev) { if (!netif_is_bond_slave(slave_dev)) { pr_err("Device %s is not bonding slave.\n", @@ -574,12 +595,6 @@ int bond_option_active_slave_set(struct bonding *bond, } } - if (!USES_PRIMARY(bond->params.mode)) { - pr_err("%s: Unable to change active slave; %s is in mode %d\n", - bond->dev->name, bond->dev->name, bond->params.mode); - return -EINVAL; - } - block_netpoll_tx(); write_lock_bh(&bond->curr_slave_lock); @@ -616,6 +631,7 @@ int bond_option_active_slave_set(struct bonding *bond, write_unlock_bh(&bond->curr_slave_lock); unblock_netpoll_tx(); + return ret; } |