Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 72be35fe authored by Jiri Pirko's avatar Jiri Pirko Committed by David S. Miller
Browse files

bonding: move mode setting into separate function

parent 0a2a78c4
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -4,7 +4,7 @@

obj-$(CONFIG_BONDING) += bonding.o

bonding-objs := bond_main.o bond_3ad.o bond_alb.o bond_sysfs.o bond_debugfs.o bond_netlink.o
bonding-objs := bond_main.o bond_3ad.o bond_alb.o bond_sysfs.o bond_debugfs.o bond_netlink.o bond_options.o

proc-$(CONFIG_PROC_FS) += bond_procfs.o
bonding-objs += $(proc-y)
+55 −0
Original line number Diff line number Diff line
/*
 * drivers/net/bond/bond_options.c - bonding options
 * Copyright (c) 2013 Jiri Pirko <jiri@resnulli.us>
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 */

#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt

#include <linux/errno.h>
#include <linux/if.h>
#include "bonding.h"

static bool bond_mode_is_valid(int mode)
{
	int i;

	for (i = 0; bond_mode_tbl[i].modename; i++);

	return mode >= 0 && mode < i;
}

int bond_option_mode_set(struct bonding *bond, int mode)
{
	if (!bond_mode_is_valid(mode)) {
		pr_err("invalid mode value %d.\n", mode);
		return -EINVAL;
	}

	if (bond->dev->flags & IFF_UP) {
		pr_err("%s: unable to update mode because interface is up.\n",
		       bond->dev->name);
		return -EPERM;
	}

	if (bond_has_slaves(bond)) {
		pr_err("%s: unable to update mode because bond has slaves.\n",
			bond->dev->name);
		return -EPERM;
	}

	if (BOND_MODE_IS_LB(mode) && bond->params.arp_interval) {
		pr_err("%s: %s mode is incompatible with arp monitoring.\n",
		       bond->dev->name, bond_mode_tbl[mode].modename);
		return -EINVAL;
	}

	/* don't cache arp_validate between modes */
	bond->params.arp_validate = BOND_ARP_VALIDATE_NONE;
	bond->params.mode = mode;
	return 0;
}
+11 −34
Original line number Diff line number Diff line
@@ -283,49 +283,26 @@ static ssize_t bonding_store_mode(struct device *d,
				  struct device_attribute *attr,
				  const char *buf, size_t count)
{
	int new_value, ret = count;
	int new_value, ret;
	struct bonding *bond = to_bond(d);

	if (!rtnl_trylock())
		return restart_syscall();

	if (bond->dev->flags & IFF_UP) {
		pr_err("unable to update mode of %s because interface is up.\n",
		       bond->dev->name);
		ret = -EPERM;
		goto out;
	}

	if (bond_has_slaves(bond)) {
		pr_err("unable to update mode of %s because it has slaves.\n",
			bond->dev->name);
		ret = -EPERM;
		goto out;
	}

	new_value = bond_parse_parm(buf, bond_mode_tbl);
	if (new_value < 0)  {
		pr_err("%s: Ignoring invalid mode value %.*s.\n",
		       bond->dev->name, (int)strlen(buf) - 1, buf);
		ret = -EINVAL;
		goto out;
	}
	if ((new_value == BOND_MODE_ALB ||
	     new_value == BOND_MODE_TLB) &&
	    bond->params.arp_interval) {
		pr_err("%s: %s mode is incompatible with arp monitoring.\n",
		       bond->dev->name, bond_mode_tbl[new_value].modename);
		ret = -EINVAL;
		goto out;
		return -EINVAL;
	}
	if (!rtnl_trylock())
		return restart_syscall();

	/* don't cache arp_validate between modes */
	bond->params.arp_validate = BOND_ARP_VALIDATE_NONE;
	bond->params.mode = new_value;
	ret = bond_option_mode_set(bond, new_value);
	if (!ret) {
		pr_info("%s: setting mode to %s (%d).\n",
			bond->dev->name, bond_mode_tbl[new_value].modename,
			new_value);
out:
		ret = count;
	}

	rtnl_unlock();
	return ret;
}
+7 −2
Original line number Diff line number Diff line
@@ -58,6 +58,11 @@
#define TX_QUEUE_OVERRIDE(mode)				\
			(((mode) == BOND_MODE_ACTIVEBACKUP) ||	\
			 ((mode) == BOND_MODE_ROUNDROBIN))

#define BOND_MODE_IS_LB(mode)			\
		(((mode) == BOND_MODE_TLB) ||	\
		 ((mode) == BOND_MODE_ALB))

/*
 * Less bad way to call ioctl from within the kernel; this needs to be
 * done some other way to get the call out of interrupt context.
@@ -259,8 +264,7 @@ static inline struct bonding *bond_get_bond_by_slave(struct slave *slave)

static inline bool bond_is_lb(const struct bonding *bond)
{
	return (bond->params.mode == BOND_MODE_TLB ||
		bond->params.mode == BOND_MODE_ALB);
	return BOND_MODE_IS_LB(bond->params.mode);
}

static inline void bond_set_active_slave(struct slave *slave)
@@ -422,6 +426,7 @@ void bond_setup(struct net_device *bond_dev);
unsigned int bond_get_num_tx_queues(void);
int bond_netlink_init(void);
void bond_netlink_fini(void);
int bond_option_mode_set(struct bonding *bond, int mode);

struct bond_net {
	struct net *		net;	/* Associated network namespace */