Merge tag 'hwmon-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/groeck...
[linux-drm-fsl-dcu.git] / drivers / net / bonding / bond_sysfs.c
index bc8fd362a5aa7624fc01a6c79722f4b57e824aef..0ec2a7e8c8a9588170c97715856e7b5f34cf7c60 100644 (file)
@@ -524,8 +524,9 @@ static ssize_t bonding_store_arp_interval(struct device *d,
                goto out;
        }
        if (bond->params.mode == BOND_MODE_ALB ||
-           bond->params.mode == BOND_MODE_TLB) {
-               pr_info("%s: ARP monitoring cannot be used with ALB/TLB. Only MII monitoring is supported on %s.\n",
+           bond->params.mode == BOND_MODE_TLB ||
+           bond->params.mode == BOND_MODE_8023AD) {
+               pr_info("%s: ARP monitoring cannot be used with ALB/TLB/802.3ad. Only MII monitoring is supported on %s.\n",
                        bond->dev->name, bond->dev->name);
                ret = -EINVAL;
                goto out;
@@ -603,15 +604,14 @@ static ssize_t bonding_store_arp_targets(struct device *d,
                return restart_syscall();
 
        targets = bond->params.arp_targets;
-       newtarget = in_aton(buf + 1);
+       if (!in4_pton(buf + 1, -1, (u8 *)&newtarget, -1, NULL) ||
+           IS_IP_TARGET_UNUSABLE_ADDRESS(newtarget)) {
+               pr_err("%s: invalid ARP target %pI4 specified for addition\n",
+                      bond->dev->name, &newtarget);
+               goto out;
+       }
        /* look for adds */
        if (buf[0] == '+') {
-               if ((newtarget == 0) || (newtarget == htonl(INADDR_BROADCAST))) {
-                       pr_err("%s: invalid ARP target %pI4 specified for addition\n",
-                              bond->dev->name, &newtarget);
-                       goto out;
-               }
-
                if (bond_get_targets_ip(targets, newtarget) != -1) { /* dup */
                        pr_err("%s: ARP target %pI4 is already present\n",
                               bond->dev->name, &newtarget);
@@ -634,12 +634,6 @@ static ssize_t bonding_store_arp_targets(struct device *d,
                targets[ind] = newtarget;
                write_unlock_bh(&bond->lock);
        } else if (buf[0] == '-')       {
-               if ((newtarget == 0) || (newtarget == htonl(INADDR_BROADCAST))) {
-                       pr_err("%s: invalid ARP target %pI4 specified for removal\n",
-                              bond->dev->name, &newtarget);
-                       goto out;
-               }
-
                ind = bond_get_targets_ip(targets, newtarget);
                if (ind == -1) {
                        pr_err("%s: unable to remove nonexistent ARP target %pI4.\n",
@@ -701,6 +695,8 @@ static ssize_t bonding_store_downdelay(struct device *d,
        int new_value, ret = count;
        struct bonding *bond = to_bond(d);
 
+       if (!rtnl_trylock())
+               return restart_syscall();
        if (!(bond->params.miimon)) {
                pr_err("%s: Unable to set down delay as MII monitoring is disabled\n",
                       bond->dev->name);
@@ -734,6 +730,7 @@ static ssize_t bonding_store_downdelay(struct device *d,
        }
 
 out:
+       rtnl_unlock();
        return ret;
 }
 static DEVICE_ATTR(downdelay, S_IRUGO | S_IWUSR,
@@ -756,6 +753,8 @@ static ssize_t bonding_store_updelay(struct device *d,
        int new_value, ret = count;
        struct bonding *bond = to_bond(d);
 
+       if (!rtnl_trylock())
+               return restart_syscall();
        if (!(bond->params.miimon)) {
                pr_err("%s: Unable to set up delay as MII monitoring is disabled\n",
                       bond->dev->name);
@@ -789,6 +788,7 @@ static ssize_t bonding_store_updelay(struct device *d,
        }
 
 out:
+       rtnl_unlock();
        return ret;
 }
 static DEVICE_ATTR(updelay, S_IRUGO | S_IWUSR,