s390: avoid inconsistent lock state in qeth
[powerpc.git] / drivers / s390 / net / qeth_sys.c
index 001497b..65ffc21 100644 (file)
@@ -328,7 +328,7 @@ qeth_dev_bufcnt_store(struct device *dev, struct device_attribute *attr, const c
 static DEVICE_ATTR(buffer_count, 0644, qeth_dev_bufcnt_show,
                qeth_dev_bufcnt_store);
 
-static inline ssize_t
+static ssize_t
 qeth_dev_route_show(struct qeth_card *card, struct qeth_routing_info *route,
                    char *buf)
 {
@@ -368,7 +368,7 @@ qeth_dev_route4_show(struct device *dev, struct device_attribute *attr, char *bu
        return qeth_dev_route_show(card, &card->options.route4, buf);
 }
 
-static inline ssize_t
+static ssize_t
 qeth_dev_route_store(struct qeth_card *card, struct qeth_routing_info *route,
                enum qeth_prot_versions prot, const char *buf, size_t count)
 {
@@ -384,8 +384,6 @@ qeth_dev_route_store(struct qeth_card *card, struct qeth_routing_info *route,
                route->type = PRIMARY_CONNECTOR;
        } else if (!strcmp(tmp, "secondary_connector")) {
                route->type = SECONDARY_CONNECTOR;
-       } else if (!strcmp(tmp, "multicast_router")) {
-               route->type = MULTICAST_ROUTER;
        } else if (!strcmp(tmp, "primary_router")) {
                route->type = PRIMARY_ROUTER;
        } else if (!strcmp(tmp, "secondary_router")) {
@@ -742,6 +740,47 @@ qeth_dev_layer2_store(struct device *dev, struct device_attribute *attr, const c
 static DEVICE_ATTR(layer2, 0644, qeth_dev_layer2_show,
                   qeth_dev_layer2_store);
 
+static ssize_t
+qeth_dev_performance_stats_show(struct device *dev, struct device_attribute *attr, char *buf)
+{
+       struct qeth_card *card = dev->driver_data;
+
+       if (!card)
+               return -EINVAL;
+
+       return sprintf(buf, "%i\n", card->options.performance_stats ? 1:0);
+}
+
+static ssize_t
+qeth_dev_performance_stats_store(struct device *dev, struct device_attribute *attr, const char *buf, size_t count)
+{
+       struct qeth_card *card = dev->driver_data;
+       char *tmp;
+       int i;
+
+       if (!card)
+               return -EINVAL;
+
+       i = simple_strtoul(buf, &tmp, 16);
+       if ((i == 0) || (i == 1)) {
+               if (i == card->options.performance_stats)
+                       return count;
+               card->options.performance_stats = i;
+               if (i == 0)
+                       memset(&card->perf_stats, 0,
+                               sizeof(struct qeth_perf_stats));
+               card->perf_stats.initial_rx_packets = card->stats.rx_packets;
+               card->perf_stats.initial_tx_packets = card->stats.tx_packets;
+       } else {
+               PRINT_WARN("performance_stats: write 0 or 1 to this file!\n");
+               return -EINVAL;
+       }
+       return count;
+}
+
+static DEVICE_ATTR(performance_stats, 0644, qeth_dev_performance_stats_show,
+                  qeth_dev_performance_stats_store);
+
 static ssize_t
 qeth_dev_large_send_show(struct device *dev, struct device_attribute *attr, char *buf)
 {
@@ -928,6 +967,7 @@ static struct device_attribute * qeth_device_attrs[] = {
        &dev_attr_canonical_macaddr,
        &dev_attr_layer2,
        &dev_attr_large_send,
+       &dev_attr_performance_stats,
        NULL,
 };
 
@@ -956,7 +996,7 @@ struct device_attribute dev_attr_##_id = {                               \
        .store  = _store,                                                    \
 };
 
-int
+static int
 qeth_check_layer2(struct qeth_card *card)
 {
        if (card->options.layer2)
@@ -1058,7 +1098,7 @@ static QETH_DEVICE_ATTR(ipato_invert4, invert4, 0644,
                        qeth_dev_ipato_invert4_show,
                        qeth_dev_ipato_invert4_store);
 
-static inline ssize_t
+static ssize_t
 qeth_dev_ipato_add_show(char *buf, struct qeth_card *card,
                        enum qeth_prot_versions proto)
 {
@@ -1104,18 +1144,18 @@ qeth_dev_ipato_add4_show(struct device *dev, struct device_attribute *attr, char
        return qeth_dev_ipato_add_show(buf, card, QETH_PROT_IPV4);
 }
 
-static inline int
+static int
 qeth_parse_ipatoe(const char* buf, enum qeth_prot_versions proto,
                  u8 *addr, int *mask_bits)
 {
        const char *start, *end;
        char *tmp;
-       char buffer[49] = {0, };
+       char buffer[40] = {0, };
 
        start = buf;
        /* get address string */
        end = strchr(start, '/');
-       if (!end || (end-start >= 49)){
+       if (!end || (end - start >= 40)){
                PRINT_WARN("Invalid format for ipato_addx/delx. "
                           "Use <ip addr>/<mask bits>\n");
                return -EINVAL;
@@ -1127,11 +1167,16 @@ qeth_parse_ipatoe(const char* buf, enum qeth_prot_versions proto,
        }
        start = end + 1;
        *mask_bits = simple_strtoul(start, &tmp, 10);
-
+       if (!strlen(start) ||
+           (tmp == start) ||
+           (*mask_bits > ((proto == QETH_PROT_IPV4) ? 32 : 128))) {
+               PRINT_WARN("Invalid mask bits for ipato_addx/delx !\n");
+               return -EINVAL;
+       }
        return 0;
 }
 
-static inline ssize_t
+static ssize_t
 qeth_dev_ipato_add_store(const char *buf, size_t count,
                         struct qeth_card *card, enum qeth_prot_versions proto)
 {
@@ -1176,7 +1221,7 @@ static QETH_DEVICE_ATTR(ipato_add4, add4, 0644,
                        qeth_dev_ipato_add4_show,
                        qeth_dev_ipato_add4_store);
 
-static inline ssize_t
+static ssize_t
 qeth_dev_ipato_del_store(const char *buf, size_t count,
                         struct qeth_card *card, enum qeth_prot_versions proto)
 {
@@ -1314,7 +1359,7 @@ static struct attribute_group qeth_device_ipato_group = {
        .attrs = (struct attribute **)qeth_ipato_device_attrs,
 };
 
-static inline ssize_t
+static ssize_t
 qeth_dev_vipa_add_show(char *buf, struct qeth_card *card,
                        enum qeth_prot_versions proto)
 {
@@ -1360,7 +1405,7 @@ qeth_dev_vipa_add4_show(struct device *dev, struct device_attribute *attr, char
        return qeth_dev_vipa_add_show(buf, card, QETH_PROT_IPV4);
 }
 
-static inline int
+static int
 qeth_parse_vipae(const char* buf, enum qeth_prot_versions proto,
                 u8 *addr)
 {
@@ -1371,7 +1416,7 @@ qeth_parse_vipae(const char* buf, enum qeth_prot_versions proto,
        return 0;
 }
 
-static inline ssize_t
+static ssize_t
 qeth_dev_vipa_add_store(const char *buf, size_t count,
                         struct qeth_card *card, enum qeth_prot_versions proto)
 {
@@ -1404,7 +1449,7 @@ static QETH_DEVICE_ATTR(vipa_add4, add4, 0644,
                        qeth_dev_vipa_add4_show,
                        qeth_dev_vipa_add4_store);
 
-static inline ssize_t
+static ssize_t
 qeth_dev_vipa_del_store(const char *buf, size_t count,
                         struct qeth_card *card, enum qeth_prot_versions proto)
 {
@@ -1495,7 +1540,7 @@ static struct attribute_group qeth_device_vipa_group = {
        .attrs = (struct attribute **)qeth_vipa_device_attrs,
 };
 
-static inline ssize_t
+static ssize_t
 qeth_dev_rxip_add_show(char *buf, struct qeth_card *card,
                       enum qeth_prot_versions proto)
 {
@@ -1541,7 +1586,7 @@ qeth_dev_rxip_add4_show(struct device *dev, struct device_attribute *attr, char
        return qeth_dev_rxip_add_show(buf, card, QETH_PROT_IPV4);
 }
 
-static inline int
+static int
 qeth_parse_rxipe(const char* buf, enum qeth_prot_versions proto,
                 u8 *addr)
 {
@@ -1552,7 +1597,7 @@ qeth_parse_rxipe(const char* buf, enum qeth_prot_versions proto,
        return 0;
 }
 
-static inline ssize_t
+static ssize_t
 qeth_dev_rxip_add_store(const char *buf, size_t count,
                        struct qeth_card *card, enum qeth_prot_versions proto)
 {
@@ -1585,7 +1630,7 @@ static QETH_DEVICE_ATTR(rxip_add4, add4, 0644,
                        qeth_dev_rxip_add4_show,
                        qeth_dev_rxip_add4_store);
 
-static inline ssize_t
+static ssize_t
 qeth_dev_rxip_del_store(const char *buf, size_t count,
                        struct qeth_card *card, enum qeth_prot_versions proto)
 {
@@ -1698,11 +1743,16 @@ qeth_create_device_attributes(struct device *dev)
                sysfs_remove_group(&dev->kobj, &qeth_device_attr_group);
                sysfs_remove_group(&dev->kobj, &qeth_device_ipato_group);
                sysfs_remove_group(&dev->kobj, &qeth_device_vipa_group);
+               return ret;
        }
-       if ((ret = sysfs_create_group(&dev->kobj, &qeth_device_blkt_group)))
+       if ((ret = sysfs_create_group(&dev->kobj, &qeth_device_blkt_group))){
+               sysfs_remove_group(&dev->kobj, &qeth_device_attr_group);
+               sysfs_remove_group(&dev->kobj, &qeth_device_ipato_group);
+               sysfs_remove_group(&dev->kobj, &qeth_device_vipa_group);
+               sysfs_remove_group(&dev->kobj, &qeth_device_rxip_group);
                return ret;
-
-       return ret;
+       }
+       return 0;
 }
 
 void