* [PATCH net-next 10/10] net: hns3: Fix loss of coal configuration while doing reset
From: Salil Mehta @ 2018-09-26 18:28 UTC (permalink / raw)
To: davem
Cc: salil.mehta, yisen.zhuang, lipeng321, mehta.salil, netdev,
linux-kernel, linuxarm, Huazhong Tan, Yunsheng Lin
In-Reply-To: <20180926182840.28392-1-salil.mehta@huawei.com>
From: Huazhong Tan <tanhuazhong@huawei.com>
The user's coal configuration will be lost after reset, so the tx_coal
and rx_coal fields are added to the struct hns_nic_priv to save the coal
configuration and used to restore the user's configuration after the reset
is complete.
Fixes: bb6b94a896d4 ("net: hns3: Add reset interface implementation in client")
Signed-off-by: Huazhong Tan <tanhuazhong@huawei.com>
Signed-off-by: Yunsheng Lin <linyunsheng@huawei.com>
Signed-off-by: Salil Mehta <salil.mehta@huawei.com>
---
drivers/net/ethernet/hisilicon/hns3/hns3_enet.c | 71 ++++++++++++-------------
drivers/net/ethernet/hisilicon/hns3/hns3_enet.h | 2 +
2 files changed, 36 insertions(+), 37 deletions(-)
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
index 8273c03..10506522 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c
@@ -225,8 +225,6 @@ void hns3_set_vector_coalesce_tx_gl(struct hns3_enet_tqp_vector *tqp_vector,
static void hns3_vector_gl_rl_init(struct hns3_enet_tqp_vector *tqp_vector,
struct hns3_nic_priv *priv)
{
- struct hnae3_handle *h = priv->ae_handle;
-
/* initialize the configuration for interrupt coalescing.
* 1. GL (Interrupt Gap Limiter)
* 2. RL (Interrupt Rate Limiter)
@@ -239,9 +237,6 @@ static void hns3_vector_gl_rl_init(struct hns3_enet_tqp_vector *tqp_vector,
tqp_vector->tx_group.coal.int_gl = HNS3_INT_GL_50K;
tqp_vector->rx_group.coal.int_gl = HNS3_INT_GL_50K;
- /* Default: disable RL */
- h->kinfo.int_rl_setting = 0;
-
tqp_vector->int_adapt_down = HNS3_INT_ADAPT_DOWN_START;
tqp_vector->rx_group.coal.flow_level = HNS3_FLOW_LOW;
tqp_vector->tx_group.coal.flow_level = HNS3_FLOW_LOW;
@@ -3490,6 +3485,31 @@ int hns3_nic_reset_all_ring(struct hnae3_handle *h)
return 0;
}
+static void hns3_store_coal(struct hns3_nic_priv *priv)
+{
+ /* ethtool only support setting and querying one coal
+ * configuation for now, so save the vector 0' coal
+ * configuation here in order to restore it.
+ */
+ memcpy(&priv->tx_coal, &priv->tqp_vector[0].tx_group.coal,
+ sizeof(struct hns3_enet_coalesce));
+ memcpy(&priv->rx_coal, &priv->tqp_vector[0].rx_group.coal,
+ sizeof(struct hns3_enet_coalesce));
+}
+
+static void hns3_restore_coal(struct hns3_nic_priv *priv)
+{
+ u16 vector_num = priv->vector_num;
+ int i;
+
+ for (i = 0; i < vector_num; i++) {
+ memcpy(&priv->tqp_vector[i].tx_group.coal, &priv->tx_coal,
+ sizeof(struct hns3_enet_coalesce));
+ memcpy(&priv->tqp_vector[i].rx_group.coal, &priv->rx_coal,
+ sizeof(struct hns3_enet_coalesce));
+ }
+}
+
static int hns3_reset_notify_down_enet(struct hnae3_handle *handle)
{
struct hnae3_knic_private_info *kinfo = &handle->kinfo;
@@ -3536,6 +3556,8 @@ static int hns3_reset_notify_init_enet(struct hnae3_handle *handle)
/* Carrier off reporting is important to ethtool even BEFORE open */
netif_carrier_off(netdev);
+ hns3_restore_coal(priv);
+
ret = hns3_nic_init_vector_data(priv);
if (ret)
return ret;
@@ -3563,6 +3585,8 @@ static int hns3_reset_notify_uninit_enet(struct hnae3_handle *handle)
return ret;
}
+ hns3_store_coal(priv);
+
ret = hns3_uninit_all_ring(priv);
if (ret)
netdev_err(netdev, "uninit ring error\n");
@@ -3597,24 +3621,7 @@ static int hns3_reset_notify(struct hnae3_handle *handle,
return ret;
}
-static void hns3_restore_coal(struct hns3_nic_priv *priv,
- struct hns3_enet_coalesce *tx,
- struct hns3_enet_coalesce *rx)
-{
- u16 vector_num = priv->vector_num;
- int i;
-
- for (i = 0; i < vector_num; i++) {
- memcpy(&priv->tqp_vector[i].tx_group.coal, tx,
- sizeof(struct hns3_enet_coalesce));
- memcpy(&priv->tqp_vector[i].rx_group.coal, rx,
- sizeof(struct hns3_enet_coalesce));
- }
-}
-
-static int hns3_modify_tqp_num(struct net_device *netdev, u16 new_tqp_num,
- struct hns3_enet_coalesce *tx,
- struct hns3_enet_coalesce *rx)
+static int hns3_modify_tqp_num(struct net_device *netdev, u16 new_tqp_num)
{
struct hns3_nic_priv *priv = netdev_priv(netdev);
struct hnae3_handle *h = hns3_get_handle(netdev);
@@ -3632,7 +3639,7 @@ static int hns3_modify_tqp_num(struct net_device *netdev, u16 new_tqp_num,
if (ret)
goto err_alloc_vector;
- hns3_restore_coal(priv, tx, rx);
+ hns3_restore_coal(priv);
ret = hns3_nic_init_vector_data(priv);
if (ret)
@@ -3664,7 +3671,6 @@ int hns3_set_channels(struct net_device *netdev,
struct hns3_nic_priv *priv = netdev_priv(netdev);
struct hnae3_handle *h = hns3_get_handle(netdev);
struct hnae3_knic_private_info *kinfo = &h->kinfo;
- struct hns3_enet_coalesce tx_coal, rx_coal;
bool if_running = netif_running(netdev);
u32 new_tqp_num = ch->combined_count;
u16 org_tqp_num;
@@ -3696,15 +3702,7 @@ int hns3_set_channels(struct net_device *netdev,
goto open_netdev;
}
- /* Changing the tqp num may also change the vector num,
- * ethtool only support setting and querying one coal
- * configuation for now, so save the vector 0' coal
- * configuation here in order to restore it.
- */
- memcpy(&tx_coal, &priv->tqp_vector[0].tx_group.coal,
- sizeof(struct hns3_enet_coalesce));
- memcpy(&rx_coal, &priv->tqp_vector[0].rx_group.coal,
- sizeof(struct hns3_enet_coalesce));
+ hns3_store_coal(priv);
hns3_nic_dealloc_vector_data(priv);
@@ -3712,10 +3710,9 @@ int hns3_set_channels(struct net_device *netdev,
hns3_put_ring_config(priv);
org_tqp_num = h->kinfo.num_tqps;
- ret = hns3_modify_tqp_num(netdev, new_tqp_num, &tx_coal, &rx_coal);
+ ret = hns3_modify_tqp_num(netdev, new_tqp_num);
if (ret) {
- ret = hns3_modify_tqp_num(netdev, org_tqp_num,
- &tx_coal, &rx_coal);
+ ret = hns3_modify_tqp_num(netdev, org_tqp_num);
if (ret) {
/* If revert to old tqp failed, fatal error occurred */
dev_err(&netdev->dev,
diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h
index 4a56c3d..27d704f 100644
--- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h
+++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.h
@@ -543,6 +543,8 @@ struct hns3_nic_priv {
/* Vxlan/Geneve information */
struct hns3_udp_tunnel udp_tnl[HNS3_UDP_TNL_MAX];
unsigned long active_vlans[BITS_TO_LONGS(VLAN_N_VID)];
+ struct hns3_enet_coalesce tx_coal;
+ struct hns3_enet_coalesce rx_coal;
};
union l3_hdr_info {
--
2.7.4
^ permalink raw reply related
* [PATCH net-next 0/9] net: bridge: convert bool options to bits
From: Nikolay Aleksandrov @ 2018-09-26 12:17 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
Hi,
A lot of boolean bridge options have been added around the net_bridge
structure resulting in holes and more importantly different cache lines
that need to be fetched in the fast path. This set moves all of those
to bits in a bitfield which resides in a hot cache line thus reducing
the size of net_bridge, the number of holes and the number of cache
lines needed for the fast path.
The set is also sent in preparation for new boolean options to avoid
spreading them in the structure and making new holes.
One nice side-effect is that we avoid potential race conditions by using
the bitops since some of the options were bits being directly set in
parallel risking hard to debug issues (has_ipv6_addr).
Before:
size: 1184, holes: 8, sum holes: 30
After:
size: 1160, holes: 2, sum holes: 3
Patch 01 is a trivial style fix
Patch 02 adds the new options bitfield and converts the vlan boolean
options to bits
Patches 03-08 convert the rest of the boolean options to bits
Patch 09 re-arranges a few fields in net_bridge to avoid fetching one
extra cache line in fast path and to further reduce size
Thanks,
Nik
Nikolay Aleksandrov (9):
net: bridge: make struct opening bracket consistent
net: bridge: add bitfield for options and convert vlan opts
net: bridge: convert nf call options to bits
net: bridge: convert group_addr_set option to a bit
net: bridge: convert and rename mcast disabled
net: bridge: convert mcast options to bits
net: bridge: convert neigh_suppress_enabled option to a bit
net: bridge: convert mtu_set_by_user to a bit
net: bridge: pack net_bridge better
net/bridge/br.c | 16 +++++++++
net/bridge/br_arp_nd_proxy.c | 13 +++++---
net/bridge/br_device.c | 6 ++--
net/bridge/br_if.c | 4 +--
net/bridge/br_input.c | 2 +-
net/bridge/br_mdb.c | 6 ++--
net/bridge/br_multicast.c | 54 +++++++++++++++---------------
net/bridge/br_netfilter_hooks.c | 7 ++--
net/bridge/br_netlink.c | 31 +++++++++--------
net/bridge/br_private.h | 74 +++++++++++++++++++++++------------------
net/bridge/br_sysfs_br.c | 32 +++++++++---------
net/bridge/br_vlan.c | 30 +++++++++--------
12 files changed, 155 insertions(+), 120 deletions(-)
--
2.11.0
^ permalink raw reply
* [PATCH net-next 1/9] net: bridge: make struct opening bracket consistent
From: Nikolay Aleksandrov @ 2018-09-26 12:17 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
Currently we have a mix of opening brackets on new lines and on the same
line, let's move them all on the same line.
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_private.h | 12 ++++--------
1 file changed, 4 insertions(+), 8 deletions(-)
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index d21035a17f4c..522d707cc533 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -54,14 +54,12 @@ typedef struct bridge_id bridge_id;
typedef struct mac_addr mac_addr;
typedef __u16 port_id;
-struct bridge_id
-{
+struct bridge_id {
unsigned char prio[2];
unsigned char addr[ETH_ALEN];
};
-struct mac_addr
-{
+struct mac_addr {
unsigned char addr[ETH_ALEN];
};
@@ -207,8 +205,7 @@ struct net_bridge_port_group {
unsigned char eth_addr[ETH_ALEN];
};
-struct net_bridge_mdb_entry
-{
+struct net_bridge_mdb_entry {
struct hlist_node hlist[2];
struct net_bridge *br;
struct net_bridge_port_group __rcu *ports;
@@ -218,8 +215,7 @@ struct net_bridge_mdb_entry
bool host_joined;
};
-struct net_bridge_mdb_htable
-{
+struct net_bridge_mdb_htable {
struct hlist_head *mhash;
struct rcu_head rcu;
struct net_bridge_mdb_htable *old;
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 2/9] net: bridge: add bitfield for options and convert vlan opts
From: Nikolay Aleksandrov @ 2018-09-26 12:17 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
Bridge options have usually been added as separate fields all over the
net_bridge struct taking up space and ending up in different cache lines.
Let's move them to a single bitfield to save up space and speedup lookups.
This patch adds a simple API for option modifying and retrieving using
bitops and converts the first user of the API - the bridge vlan options
(vlan_enabled and vlan_stats_enabled).
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br.c | 16 ++++++++++++++++
net/bridge/br_netlink.c | 3 ++-
net/bridge/br_private.h | 16 ++++++++++++++--
net/bridge/br_sysfs_br.c | 4 ++--
net/bridge/br_vlan.c | 28 +++++++++++++++-------------
5 files changed, 49 insertions(+), 18 deletions(-)
diff --git a/net/bridge/br.c b/net/bridge/br.c
index b0a0b82e2d91..e411e40333e2 100644
--- a/net/bridge/br.c
+++ b/net/bridge/br.c
@@ -175,6 +175,22 @@ static struct notifier_block br_switchdev_notifier = {
.notifier_call = br_switchdev_event,
};
+void br_opt_toggle(struct net_bridge *br, enum net_bridge_opts opt, bool on)
+{
+ bool cur = !!br_opt_get(br, opt);
+
+ br_debug(br, "toggle option: %d state: %d -> %d\n",
+ opt, cur, on);
+
+ if (cur == on)
+ return;
+
+ if (on)
+ set_bit(opt, &br->options);
+ else
+ clear_bit(opt, &br->options);
+}
+
static void __net_exit br_net_exit(struct net *net)
{
struct net_device *dev;
diff --git a/net/bridge/br_netlink.c b/net/bridge/br_netlink.c
index ec2b58a09f76..6a53caff2d31 100644
--- a/net/bridge/br_netlink.c
+++ b/net/bridge/br_netlink.c
@@ -1416,7 +1416,8 @@ static int br_fill_info(struct sk_buff *skb, const struct net_device *brdev)
#ifdef CONFIG_BRIDGE_VLAN_FILTERING
if (nla_put_be16(skb, IFLA_BR_VLAN_PROTOCOL, br->vlan_proto) ||
nla_put_u16(skb, IFLA_BR_VLAN_DEFAULT_PVID, br->default_pvid) ||
- nla_put_u8(skb, IFLA_BR_VLAN_STATS_ENABLED, br->vlan_stats_enabled))
+ nla_put_u8(skb, IFLA_BR_VLAN_STATS_ENABLED,
+ br_opt_get(br, BROPT_VLAN_STATS_ENABLED)))
return -EMSGSIZE;
#endif
#ifdef CONFIG_BRIDGE_IGMP_SNOOPING
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index 522d707cc533..0abb632283ff 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -306,16 +306,20 @@ static inline struct net_bridge_port *br_port_get_rtnl_rcu(const struct net_devi
rcu_dereference_rtnl(dev->rx_handler_data) : NULL;
}
+enum net_bridge_opts {
+ BROPT_VLAN_ENABLED,
+ BROPT_VLAN_STATS_ENABLED,
+};
+
struct net_bridge {
spinlock_t lock;
spinlock_t hash_lock;
struct list_head port_list;
struct net_device *dev;
struct pcpu_sw_netstats __percpu *stats;
+ unsigned long options;
/* These fields are accessed on each packet */
#ifdef CONFIG_BRIDGE_VLAN_FILTERING
- u8 vlan_enabled;
- u8 vlan_stats_enabled;
__be16 vlan_proto;
u16 default_pvid;
struct net_bridge_vlan_group __rcu *vlgrp;
@@ -489,6 +493,14 @@ static inline bool br_vlan_should_use(const struct net_bridge_vlan *v)
return true;
}
+static inline int br_opt_get(const struct net_bridge *br,
+ enum net_bridge_opts opt)
+{
+ return test_bit(opt, &br->options);
+}
+
+void br_opt_toggle(struct net_bridge *br, enum net_bridge_opts opt, bool on);
+
/* br_device.c */
void br_dev_setup(struct net_device *dev);
void br_dev_delete(struct net_device *dev, struct list_head *list);
diff --git a/net/bridge/br_sysfs_br.c b/net/bridge/br_sysfs_br.c
index 0318a69888d4..9f1f3866c833 100644
--- a/net/bridge/br_sysfs_br.c
+++ b/net/bridge/br_sysfs_br.c
@@ -743,7 +743,7 @@ static ssize_t vlan_filtering_show(struct device *d,
char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%d\n", br->vlan_enabled);
+ return sprintf(buf, "%d\n", br_opt_get(br, BROPT_VLAN_ENABLED));
}
static ssize_t vlan_filtering_store(struct device *d,
@@ -791,7 +791,7 @@ static ssize_t vlan_stats_enabled_show(struct device *d,
char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%u\n", br->vlan_stats_enabled);
+ return sprintf(buf, "%u\n", br_opt_get(br, BROPT_VLAN_STATS_ENABLED));
}
static ssize_t vlan_stats_enabled_store(struct device *d,
diff --git a/net/bridge/br_vlan.c b/net/bridge/br_vlan.c
index bb6ba794864f..61d698bfe2b7 100644
--- a/net/bridge/br_vlan.c
+++ b/net/bridge/br_vlan.c
@@ -386,7 +386,7 @@ struct sk_buff *br_handle_vlan(struct net_bridge *br,
return NULL;
}
}
- if (br->vlan_stats_enabled) {
+ if (br_opt_get(br, BROPT_VLAN_STATS_ENABLED)) {
stats = this_cpu_ptr(v->stats);
u64_stats_update_begin(&stats->syncp);
stats->tx_bytes += skb->len;
@@ -475,14 +475,14 @@ static bool __allowed_ingress(const struct net_bridge *br,
skb->vlan_tci |= pvid;
/* if stats are disabled we can avoid the lookup */
- if (!br->vlan_stats_enabled)
+ if (!br_opt_get(br, BROPT_VLAN_STATS_ENABLED))
return true;
}
v = br_vlan_find(vg, *vid);
if (!v || !br_vlan_should_use(v))
goto drop;
- if (br->vlan_stats_enabled) {
+ if (br_opt_get(br, BROPT_VLAN_STATS_ENABLED)) {
stats = this_cpu_ptr(v->stats);
u64_stats_update_begin(&stats->syncp);
stats->rx_bytes += skb->len;
@@ -504,7 +504,7 @@ bool br_allowed_ingress(const struct net_bridge *br,
/* If VLAN filtering is disabled on the bridge, all packets are
* permitted.
*/
- if (!br->vlan_enabled) {
+ if (!br_opt_get(br, BROPT_VLAN_ENABLED)) {
BR_INPUT_SKB_CB(skb)->vlan_filtered = false;
return true;
}
@@ -538,7 +538,7 @@ bool br_should_learn(struct net_bridge_port *p, struct sk_buff *skb, u16 *vid)
struct net_bridge *br = p->br;
/* If filtering was disabled at input, let it pass. */
- if (!br->vlan_enabled)
+ if (!br_opt_get(br, BROPT_VLAN_ENABLED))
return true;
vg = nbp_vlan_group_rcu(p);
@@ -699,7 +699,8 @@ static void recalculate_group_addr(struct net_bridge *br)
return;
spin_lock_bh(&br->lock);
- if (!br->vlan_enabled || br->vlan_proto == htons(ETH_P_8021Q)) {
+ if (!br_opt_get(br, BROPT_VLAN_ENABLED) ||
+ br->vlan_proto == htons(ETH_P_8021Q)) {
/* Bridge Group Address */
br->group_addr[5] = 0x00;
} else { /* vlan_enabled && ETH_P_8021AD */
@@ -712,7 +713,8 @@ static void recalculate_group_addr(struct net_bridge *br)
/* Must be protected by RTNL. */
void br_recalculate_fwd_mask(struct net_bridge *br)
{
- if (!br->vlan_enabled || br->vlan_proto == htons(ETH_P_8021Q))
+ if (!br_opt_get(br, BROPT_VLAN_ENABLED) ||
+ br->vlan_proto == htons(ETH_P_8021Q))
br->group_fwd_mask_required = BR_GROUPFWD_DEFAULT;
else /* vlan_enabled && ETH_P_8021AD */
br->group_fwd_mask_required = BR_GROUPFWD_8021AD &
@@ -729,14 +731,14 @@ int __br_vlan_filter_toggle(struct net_bridge *br, unsigned long val)
};
int err;
- if (br->vlan_enabled == val)
+ if (br_opt_get(br, BROPT_VLAN_ENABLED) == !!val)
return 0;
err = switchdev_port_attr_set(br->dev, &attr);
if (err && err != -EOPNOTSUPP)
return err;
- br->vlan_enabled = val;
+ br_opt_toggle(br, BROPT_VLAN_ENABLED, !!val);
br_manage_promisc(br);
recalculate_group_addr(br);
br_recalculate_fwd_mask(br);
@@ -753,7 +755,7 @@ bool br_vlan_enabled(const struct net_device *dev)
{
struct net_bridge *br = netdev_priv(dev);
- return !!br->vlan_enabled;
+ return br_opt_get(br, BROPT_VLAN_ENABLED);
}
EXPORT_SYMBOL_GPL(br_vlan_enabled);
@@ -819,7 +821,7 @@ int br_vlan_set_stats(struct net_bridge *br, unsigned long val)
switch (val) {
case 0:
case 1:
- br->vlan_stats_enabled = val;
+ br_opt_toggle(br, BROPT_VLAN_STATS_ENABLED, !!val);
break;
default:
return -EINVAL;
@@ -964,7 +966,7 @@ int br_vlan_set_default_pvid(struct net_bridge *br, unsigned long val)
goto out;
/* Only allow default pvid change when filtering is disabled */
- if (br->vlan_enabled) {
+ if (br_opt_get(br, BROPT_VLAN_ENABLED)) {
pr_info_once("Please disable vlan filtering to change default_pvid\n");
err = -EPERM;
goto out;
@@ -1018,7 +1020,7 @@ int nbp_vlan_init(struct net_bridge_port *p)
.orig_dev = p->br->dev,
.id = SWITCHDEV_ATTR_ID_BRIDGE_VLAN_FILTERING,
.flags = SWITCHDEV_F_SKIP_EOPNOTSUPP,
- .u.vlan_filtering = p->br->vlan_enabled,
+ .u.vlan_filtering = br_opt_get(p->br, BROPT_VLAN_ENABLED),
};
struct net_bridge_vlan_group *vg;
int ret = -ENOMEM;
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 3/9] net: bridge: convert nf call options to bits
From: Nikolay Aleksandrov @ 2018-09-26 12:17 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
No functional change, convert of nf_call_[ip|ip6|arp]tables to bits.
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_netfilter_hooks.c | 7 ++++---
net/bridge/br_netlink.c | 12 ++++++------
net/bridge/br_private.h | 6 +++---
net/bridge/br_sysfs_br.c | 12 ++++++------
4 files changed, 19 insertions(+), 18 deletions(-)
diff --git a/net/bridge/br_netfilter_hooks.c b/net/bridge/br_netfilter_hooks.c
index 6e0dc6bcd32a..e0a3b038d052 100644
--- a/net/bridge/br_netfilter_hooks.c
+++ b/net/bridge/br_netfilter_hooks.c
@@ -487,14 +487,15 @@ static unsigned int br_nf_pre_routing(void *priv,
br = p->br;
if (IS_IPV6(skb) || IS_VLAN_IPV6(skb) || IS_PPPOE_IPV6(skb)) {
- if (!brnf_call_ip6tables && !br->nf_call_ip6tables)
+ if (!brnf_call_ip6tables &&
+ !br_opt_get(br, BROPT_NF_CALL_IP6TABLES))
return NF_ACCEPT;
nf_bridge_pull_encap_header_rcsum(skb);
return br_nf_pre_routing_ipv6(priv, skb, state);
}
- if (!brnf_call_iptables && !br->nf_call_iptables)
+ if (!brnf_call_iptables && !br_opt_get(br, BROPT_NF_CALL_IPTABLES))
return NF_ACCEPT;
if (!IS_IP(skb) && !IS_VLAN_IP(skb) && !IS_PPPOE_IP(skb))
@@ -636,7 +637,7 @@ static unsigned int br_nf_forward_arp(void *priv,
return NF_ACCEPT;
br = p->br;
- if (!brnf_call_arptables && !br->nf_call_arptables)
+ if (!brnf_call_arptables && !br_opt_get(br, BROPT_NF_CALL_ARPTABLES))
return NF_ACCEPT;
if (!IS_ARP(skb)) {
diff --git a/net/bridge/br_netlink.c b/net/bridge/br_netlink.c
index 6a53caff2d31..521893df0c2a 100644
--- a/net/bridge/br_netlink.c
+++ b/net/bridge/br_netlink.c
@@ -1271,19 +1271,19 @@ static int br_changelink(struct net_device *brdev, struct nlattr *tb[],
if (data[IFLA_BR_NF_CALL_IPTABLES]) {
u8 val = nla_get_u8(data[IFLA_BR_NF_CALL_IPTABLES]);
- br->nf_call_iptables = val ? true : false;
+ br_opt_toggle(br, BROPT_NF_CALL_IPTABLES, !!val);
}
if (data[IFLA_BR_NF_CALL_IP6TABLES]) {
u8 val = nla_get_u8(data[IFLA_BR_NF_CALL_IP6TABLES]);
- br->nf_call_ip6tables = val ? true : false;
+ br_opt_toggle(br, BROPT_NF_CALL_IP6TABLES, !!val);
}
if (data[IFLA_BR_NF_CALL_ARPTABLES]) {
u8 val = nla_get_u8(data[IFLA_BR_NF_CALL_ARPTABLES]);
- br->nf_call_arptables = val ? true : false;
+ br_opt_toggle(br, BROPT_NF_CALL_ARPTABLES, !!val);
}
#endif
@@ -1470,11 +1470,11 @@ static int br_fill_info(struct sk_buff *skb, const struct net_device *brdev)
#endif
#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
if (nla_put_u8(skb, IFLA_BR_NF_CALL_IPTABLES,
- br->nf_call_iptables ? 1 : 0) ||
+ br_opt_get(br, BROPT_NF_CALL_IPTABLES) ? 1 : 0) ||
nla_put_u8(skb, IFLA_BR_NF_CALL_IP6TABLES,
- br->nf_call_ip6tables ? 1 : 0) ||
+ br_opt_get(br, BROPT_NF_CALL_IP6TABLES) ? 1 : 0) ||
nla_put_u8(skb, IFLA_BR_NF_CALL_ARPTABLES,
- br->nf_call_arptables ? 1 : 0))
+ br_opt_get(br, BROPT_NF_CALL_ARPTABLES) ? 1 : 0))
return -EMSGSIZE;
#endif
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index 0abb632283ff..d8eadab09d7d 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -309,6 +309,9 @@ static inline struct net_bridge_port *br_port_get_rtnl_rcu(const struct net_devi
enum net_bridge_opts {
BROPT_VLAN_ENABLED,
BROPT_VLAN_STATS_ENABLED,
+ BROPT_NF_CALL_IPTABLES,
+ BROPT_NF_CALL_IP6TABLES,
+ BROPT_NF_CALL_ARPTABLES,
};
struct net_bridge {
@@ -331,9 +334,6 @@ struct net_bridge {
struct rtable fake_rtable;
struct rt6_info fake_rt6_info;
};
- bool nf_call_iptables;
- bool nf_call_ip6tables;
- bool nf_call_arptables;
#endif
u16 group_fwd_mask;
u16 group_fwd_mask_required;
diff --git a/net/bridge/br_sysfs_br.c b/net/bridge/br_sysfs_br.c
index 9f1f3866c833..0f8545c94948 100644
--- a/net/bridge/br_sysfs_br.c
+++ b/net/bridge/br_sysfs_br.c
@@ -678,12 +678,12 @@ static ssize_t nf_call_iptables_show(
struct device *d, struct device_attribute *attr, char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%u\n", br->nf_call_iptables);
+ return sprintf(buf, "%u\n", br_opt_get(br, BROPT_NF_CALL_IPTABLES));
}
static int set_nf_call_iptables(struct net_bridge *br, unsigned long val)
{
- br->nf_call_iptables = val ? true : false;
+ br_opt_toggle(br, BROPT_NF_CALL_IPTABLES, !!val);
return 0;
}
@@ -699,12 +699,12 @@ static ssize_t nf_call_ip6tables_show(
struct device *d, struct device_attribute *attr, char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%u\n", br->nf_call_ip6tables);
+ return sprintf(buf, "%u\n", br_opt_get(br, BROPT_NF_CALL_IP6TABLES));
}
static int set_nf_call_ip6tables(struct net_bridge *br, unsigned long val)
{
- br->nf_call_ip6tables = val ? true : false;
+ br_opt_toggle(br, BROPT_NF_CALL_IP6TABLES, !!val);
return 0;
}
@@ -720,12 +720,12 @@ static ssize_t nf_call_arptables_show(
struct device *d, struct device_attribute *attr, char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%u\n", br->nf_call_arptables);
+ return sprintf(buf, "%u\n", br_opt_get(br, BROPT_NF_CALL_ARPTABLES));
}
static int set_nf_call_arptables(struct net_bridge *br, unsigned long val)
{
- br->nf_call_arptables = val ? true : false;
+ br_opt_toggle(br, BROPT_NF_CALL_ARPTABLES, !!val);
return 0;
}
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 4/9] net: bridge: convert group_addr_set option to a bit
From: Nikolay Aleksandrov @ 2018-09-26 12:17 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
Convert group_addr_set internal bridge opt to a bit.
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_netlink.c | 2 +-
net/bridge/br_private.h | 2 +-
net/bridge/br_sysfs_br.c | 2 +-
net/bridge/br_vlan.c | 2 +-
4 files changed, 4 insertions(+), 4 deletions(-)
diff --git a/net/bridge/br_netlink.c b/net/bridge/br_netlink.c
index 521893df0c2a..b00ccf35c35d 100644
--- a/net/bridge/br_netlink.c
+++ b/net/bridge/br_netlink.c
@@ -1139,7 +1139,7 @@ static int br_changelink(struct net_device *brdev, struct nlattr *tb[],
spin_lock_bh(&br->lock);
memcpy(br->group_addr, new_addr, sizeof(br->group_addr));
spin_unlock_bh(&br->lock);
- br->group_addr_set = true;
+ br_opt_toggle(br, BROPT_GROUP_ADDR_SET, true);
br_recalculate_fwd_mask(br);
}
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index d8eadab09d7d..dda117ce386e 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -312,6 +312,7 @@ enum net_bridge_opts {
BROPT_NF_CALL_IPTABLES,
BROPT_NF_CALL_IP6TABLES,
BROPT_NF_CALL_ARPTABLES,
+ BROPT_GROUP_ADDR_SET,
};
struct net_bridge {
@@ -355,7 +356,6 @@ struct net_bridge {
unsigned long bridge_ageing_time;
u8 group_addr[ETH_ALEN];
- bool group_addr_set;
enum {
BR_NO_STP, /* no spanning tree */
diff --git a/net/bridge/br_sysfs_br.c b/net/bridge/br_sysfs_br.c
index 0f8545c94948..4c2d56354d89 100644
--- a/net/bridge/br_sysfs_br.c
+++ b/net/bridge/br_sysfs_br.c
@@ -303,7 +303,7 @@ static ssize_t group_addr_store(struct device *d,
ether_addr_copy(br->group_addr, new_addr);
spin_unlock_bh(&br->lock);
- br->group_addr_set = true;
+ br_opt_toggle(br, BROPT_GROUP_ADDR_SET, true);
br_recalculate_fwd_mask(br);
netdev_state_change(br->dev);
diff --git a/net/bridge/br_vlan.c b/net/bridge/br_vlan.c
index 61d698bfe2b7..5942e03dd845 100644
--- a/net/bridge/br_vlan.c
+++ b/net/bridge/br_vlan.c
@@ -695,7 +695,7 @@ struct net_bridge_vlan *br_vlan_find(struct net_bridge_vlan_group *vg, u16 vid)
/* Must be protected by RTNL. */
static void recalculate_group_addr(struct net_bridge *br)
{
- if (br->group_addr_set)
+ if (br_opt_get(br, BROPT_GROUP_ADDR_SET))
return;
spin_lock_bh(&br->lock);
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 5/9] net: bridge: convert and rename mcast disabled
From: Nikolay Aleksandrov @ 2018-09-26 12:17 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
Convert mcast disabled to an option bit and while doing so convert the
logic to check if multicast is enabled instead. That is make the logic
follow the option value - if it's set then mcast is enabled and vice versa.
This avoids a few confusing places where we inverted the value that's being
set to follow the mcast_disabled logic.
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_mdb.c | 6 +++---
net/bridge/br_multicast.c | 32 +++++++++++++++++---------------
net/bridge/br_netlink.c | 3 ++-
net/bridge/br_private.h | 2 +-
net/bridge/br_sysfs_br.c | 2 +-
5 files changed, 24 insertions(+), 21 deletions(-)
diff --git a/net/bridge/br_mdb.c b/net/bridge/br_mdb.c
index 6d9f48bd374a..a4a848bf827b 100644
--- a/net/bridge/br_mdb.c
+++ b/net/bridge/br_mdb.c
@@ -84,7 +84,7 @@ static int br_mdb_fill_info(struct sk_buff *skb, struct netlink_callback *cb,
int i, err = 0;
int idx = 0, s_idx = cb->args[1];
- if (br->multicast_disabled)
+ if (!br_opt_get(br, BROPT_MULTICAST_ENABLED))
return 0;
mdb = rcu_dereference(br->mdb);
@@ -598,7 +598,7 @@ static int __br_mdb_add(struct net *net, struct net_bridge *br,
struct net_bridge_port *p;
int ret;
- if (!netif_running(br->dev) || br->multicast_disabled)
+ if (!netif_running(br->dev) || !br_opt_get(br, BROPT_MULTICAST_ENABLED))
return -EINVAL;
dev = __dev_get_by_index(net, entry->ifindex);
@@ -673,7 +673,7 @@ static int __br_mdb_del(struct net_bridge *br, struct br_mdb_entry *entry)
struct br_ip ip;
int err = -EINVAL;
- if (!netif_running(br->dev) || br->multicast_disabled)
+ if (!netif_running(br->dev) || !br_opt_get(br, BROPT_MULTICAST_ENABLED))
return -EINVAL;
__mdb_entry_to_br_ip(entry, &ip);
diff --git a/net/bridge/br_multicast.c b/net/bridge/br_multicast.c
index 20ed7adcf1cc..ed6c33adc747 100644
--- a/net/bridge/br_multicast.c
+++ b/net/bridge/br_multicast.c
@@ -158,7 +158,7 @@ struct net_bridge_mdb_entry *br_mdb_get(struct net_bridge *br,
struct net_bridge_mdb_htable *mdb = rcu_dereference(br->mdb);
struct br_ip ip;
- if (br->multicast_disabled)
+ if (!br_opt_get(br, BROPT_MULTICAST_ENABLED))
return NULL;
if (BR_INPUT_SKB_CB(skb)->igmp)
@@ -628,7 +628,7 @@ static struct net_bridge_mdb_entry *br_multicast_get_group(
port ? port->dev->name : br->dev->name);
err = -E2BIG;
disable:
- br->multicast_disabled = 1;
+ br_opt_toggle(br, BROPT_MULTICAST_ENABLED, false);
goto err;
}
}
@@ -894,7 +894,7 @@ static void br_multicast_querier_expired(struct net_bridge *br,
struct bridge_mcast_own_query *query)
{
spin_lock(&br->multicast_lock);
- if (!netif_running(br->dev) || br->multicast_disabled)
+ if (!netif_running(br->dev) || !br_opt_get(br, BROPT_MULTICAST_ENABLED))
goto out;
br_multicast_start_querier(br, query);
@@ -965,7 +965,8 @@ static void br_multicast_send_query(struct net_bridge *br,
struct br_ip br_group;
unsigned long time;
- if (!netif_running(br->dev) || br->multicast_disabled ||
+ if (!netif_running(br->dev) ||
+ !br_opt_get(br, BROPT_MULTICAST_ENABLED) ||
!br->multicast_querier)
return;
@@ -1036,7 +1037,7 @@ static void br_mc_disabled_update(struct net_device *dev, bool value)
.orig_dev = dev,
.id = SWITCHDEV_ATTR_ID_BRIDGE_MC_DISABLED,
.flags = SWITCHDEV_F_DEFER,
- .u.mc_disabled = value,
+ .u.mc_disabled = !value,
};
switchdev_port_attr_set(dev, &attr);
@@ -1054,7 +1055,8 @@ int br_multicast_add_port(struct net_bridge_port *port)
timer_setup(&port->ip6_own_query.timer,
br_ip6_multicast_port_query_expired, 0);
#endif
- br_mc_disabled_update(port->dev, port->br->multicast_disabled);
+ br_mc_disabled_update(port->dev,
+ br_opt_get(port->br, BROPT_MULTICAST_ENABLED));
port->mcast_stats = netdev_alloc_pcpu_stats(struct bridge_mcast_stats);
if (!port->mcast_stats)
@@ -1091,7 +1093,7 @@ static void __br_multicast_enable_port(struct net_bridge_port *port)
{
struct net_bridge *br = port->br;
- if (br->multicast_disabled || !netif_running(br->dev))
+ if (!br_opt_get(br, BROPT_MULTICAST_ENABLED) || !netif_running(br->dev))
return;
br_multicast_enable(&port->ip4_own_query);
@@ -1904,7 +1906,7 @@ int br_multicast_rcv(struct net_bridge *br, struct net_bridge_port *port,
BR_INPUT_SKB_CB(skb)->igmp = 0;
BR_INPUT_SKB_CB(skb)->mrouters_only = 0;
- if (br->multicast_disabled)
+ if (!br_opt_get(br, BROPT_MULTICAST_ENABLED))
return 0;
switch (skb->protocol) {
@@ -1998,7 +2000,7 @@ static void __br_multicast_open(struct net_bridge *br,
{
query->startup_sent = 0;
- if (br->multicast_disabled)
+ if (!br_opt_get(br, BROPT_MULTICAST_ENABLED))
return;
mod_timer(&query->timer, jiffies);
@@ -2173,12 +2175,12 @@ int br_multicast_toggle(struct net_bridge *br, unsigned long val)
int err = 0;
spin_lock_bh(&br->multicast_lock);
- if (br->multicast_disabled == !val)
+ if (!!br_opt_get(br, BROPT_MULTICAST_ENABLED) == !!val)
goto unlock;
- br_mc_disabled_update(br->dev, !val);
- br->multicast_disabled = !val;
- if (br->multicast_disabled)
+ br_mc_disabled_update(br->dev, val);
+ br_opt_toggle(br, BROPT_MULTICAST_ENABLED, !!val);
+ if (!br_opt_get(br, BROPT_MULTICAST_ENABLED))
goto unlock;
if (!netif_running(br->dev))
@@ -2189,7 +2191,7 @@ int br_multicast_toggle(struct net_bridge *br, unsigned long val)
if (mdb->old) {
err = -EEXIST;
rollback:
- br->multicast_disabled = !!val;
+ br_opt_toggle(br, BROPT_MULTICAST_ENABLED, false);
goto unlock;
}
@@ -2213,7 +2215,7 @@ bool br_multicast_enabled(const struct net_device *dev)
{
struct net_bridge *br = netdev_priv(dev);
- return !br->multicast_disabled;
+ return !!br_opt_get(br, BROPT_MULTICAST_ENABLED);
}
EXPORT_SYMBOL_GPL(br_multicast_enabled);
diff --git a/net/bridge/br_netlink.c b/net/bridge/br_netlink.c
index b00ccf35c35d..1d276b7b27e0 100644
--- a/net/bridge/br_netlink.c
+++ b/net/bridge/br_netlink.c
@@ -1422,7 +1422,8 @@ static int br_fill_info(struct sk_buff *skb, const struct net_device *brdev)
#endif
#ifdef CONFIG_BRIDGE_IGMP_SNOOPING
if (nla_put_u8(skb, IFLA_BR_MCAST_ROUTER, br->multicast_router) ||
- nla_put_u8(skb, IFLA_BR_MCAST_SNOOPING, !br->multicast_disabled) ||
+ nla_put_u8(skb, IFLA_BR_MCAST_SNOOPING,
+ br_opt_get(br, BROPT_MULTICAST_ENABLED)) ||
nla_put_u8(skb, IFLA_BR_MCAST_QUERY_USE_IFADDR,
br->multicast_query_use_ifaddr) ||
nla_put_u8(skb, IFLA_BR_MCAST_QUERIER, br->multicast_querier) ||
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index dda117ce386e..fb1a266cdac8 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -313,6 +313,7 @@ enum net_bridge_opts {
BROPT_NF_CALL_IP6TABLES,
BROPT_NF_CALL_ARPTABLES,
BROPT_GROUP_ADDR_SET,
+ BROPT_MULTICAST_ENABLED,
};
struct net_bridge {
@@ -366,7 +367,6 @@ struct net_bridge {
#ifdef CONFIG_BRIDGE_IGMP_SNOOPING
unsigned char multicast_router;
- u8 multicast_disabled:1;
u8 multicast_querier:1;
u8 multicast_query_use_ifaddr:1;
u8 has_ipv6_addr:1;
diff --git a/net/bridge/br_sysfs_br.c b/net/bridge/br_sysfs_br.c
index 4c2d56354d89..bf6f409a83e1 100644
--- a/net/bridge/br_sysfs_br.c
+++ b/net/bridge/br_sysfs_br.c
@@ -349,7 +349,7 @@ static ssize_t multicast_snooping_show(struct device *d,
char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%d\n", !br->multicast_disabled);
+ return sprintf(buf, "%d\n", br_opt_get(br, BROPT_MULTICAST_ENABLED));
}
static ssize_t multicast_snooping_store(struct device *d,
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 6/9] net: bridge: convert mcast options to bits
From: Nikolay Aleksandrov @ 2018-09-26 12:17 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
This patch converts the rest of the mcast options to bits. It also packs
the mcast options a little better by moving multicast_mld_version to an
existing hole, reducing the net_bridge size by 8 bytes.
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_multicast.c | 22 ++++++++++------------
net/bridge/br_netlink.c | 11 ++++++-----
net/bridge/br_private.h | 20 ++++++++++----------
net/bridge/br_sysfs_br.c | 12 +++++++-----
4 files changed, 33 insertions(+), 32 deletions(-)
diff --git a/net/bridge/br_multicast.c b/net/bridge/br_multicast.c
index ed6c33adc747..928024d8360d 100644
--- a/net/bridge/br_multicast.c
+++ b/net/bridge/br_multicast.c
@@ -411,7 +411,7 @@ static struct sk_buff *br_ip4_multicast_alloc_query(struct net_bridge *br,
iph->frag_off = htons(IP_DF);
iph->ttl = 1;
iph->protocol = IPPROTO_IGMP;
- iph->saddr = br->multicast_query_use_ifaddr ?
+ iph->saddr = br_opt_get(br, BROPT_MULTICAST_QUERY_USE_IFADDR) ?
inet_select_addr(br->dev, 0, RT_SCOPE_LINK) : 0;
iph->daddr = htonl(INADDR_ALLHOSTS_GROUP);
((u8 *)&iph[1])[0] = IPOPT_RA;
@@ -503,11 +503,11 @@ static struct sk_buff *br_ip6_multicast_alloc_query(struct net_bridge *br,
if (ipv6_dev_get_saddr(dev_net(br->dev), br->dev, &ip6h->daddr, 0,
&ip6h->saddr)) {
kfree_skb(skb);
- br->has_ipv6_addr = 0;
+ br_opt_toggle(br, BROPT_HAS_IPV6_ADDR, false);
return NULL;
}
- br->has_ipv6_addr = 1;
+ br_opt_toggle(br, BROPT_HAS_IPV6_ADDR, true);
ipv6_eth_mc_map(&ip6h->daddr, eth->h_dest);
hopopt = (u8 *)(ip6h + 1);
@@ -967,7 +967,7 @@ static void br_multicast_send_query(struct net_bridge *br,
if (!netif_running(br->dev) ||
!br_opt_get(br, BROPT_MULTICAST_ENABLED) ||
- !br->multicast_querier)
+ !br_opt_get(br, BROPT_MULTICAST_QUERIER))
return;
memset(&br_group.u, 0, sizeof(br_group.u));
@@ -1636,7 +1636,7 @@ br_multicast_leave_group(struct net_bridge *br,
if (timer_pending(&other_query->timer))
goto out;
- if (br->multicast_querier) {
+ if (br_opt_get(br, BROPT_MULTICAST_QUERIER)) {
__br_multicast_send_query(br, port, &mp->addr);
time = jiffies + br->multicast_last_member_count *
@@ -1748,7 +1748,7 @@ static void br_multicast_err_count(const struct net_bridge *br,
struct bridge_mcast_stats __percpu *stats;
struct bridge_mcast_stats *pstats;
- if (!br->multicast_stats_enabled)
+ if (!br_opt_get(br, BROPT_MULTICAST_STATS_ENABLED))
return;
if (p)
@@ -1958,8 +1958,6 @@ void br_multicast_init(struct net_bridge *br)
br->hash_max = 512;
br->multicast_router = MDB_RTR_TYPE_TEMP_QUERY;
- br->multicast_querier = 0;
- br->multicast_query_use_ifaddr = 0;
br->multicast_last_member_count = 2;
br->multicast_startup_query_count = 2;
@@ -1978,7 +1976,7 @@ void br_multicast_init(struct net_bridge *br)
br->ip6_other_query.delay_time = 0;
br->ip6_querier.port = NULL;
#endif
- br->has_ipv6_addr = 1;
+ br_opt_toggle(br, BROPT_HAS_IPV6_ADDR, true);
spin_lock_init(&br->multicast_lock);
timer_setup(&br->multicast_router_timer,
@@ -2238,10 +2236,10 @@ int br_multicast_set_querier(struct net_bridge *br, unsigned long val)
val = !!val;
spin_lock_bh(&br->multicast_lock);
- if (br->multicast_querier == val)
+ if (br_opt_get(br, BROPT_MULTICAST_QUERIER) == val)
goto unlock;
- br->multicast_querier = val;
+ br_opt_toggle(br, BROPT_MULTICAST_QUERIER, !!val);
if (!val)
goto unlock;
@@ -2562,7 +2560,7 @@ void br_multicast_count(struct net_bridge *br, const struct net_bridge_port *p,
struct bridge_mcast_stats __percpu *stats;
/* if multicast_disabled is true then igmp type can't be set */
- if (!type || !br->multicast_stats_enabled)
+ if (!type || !br_opt_get(br, BROPT_MULTICAST_STATS_ENABLED))
return;
if (p)
diff --git a/net/bridge/br_netlink.c b/net/bridge/br_netlink.c
index 1d276b7b27e0..e5a5bc5d5232 100644
--- a/net/bridge/br_netlink.c
+++ b/net/bridge/br_netlink.c
@@ -1167,7 +1167,7 @@ static int br_changelink(struct net_device *brdev, struct nlattr *tb[],
u8 val;
val = nla_get_u8(data[IFLA_BR_MCAST_QUERY_USE_IFADDR]);
- br->multicast_query_use_ifaddr = !!val;
+ br_opt_toggle(br, BROPT_MULTICAST_QUERY_USE_IFADDR, !!val);
}
if (data[IFLA_BR_MCAST_QUERIER]) {
@@ -1244,7 +1244,7 @@ static int br_changelink(struct net_device *brdev, struct nlattr *tb[],
__u8 mcast_stats;
mcast_stats = nla_get_u8(data[IFLA_BR_MCAST_STATS_ENABLED]);
- br->multicast_stats_enabled = !!mcast_stats;
+ br_opt_toggle(br, BROPT_MULTICAST_STATS_ENABLED, !!mcast_stats);
}
if (data[IFLA_BR_MCAST_IGMP_VERSION]) {
@@ -1425,10 +1425,11 @@ static int br_fill_info(struct sk_buff *skb, const struct net_device *brdev)
nla_put_u8(skb, IFLA_BR_MCAST_SNOOPING,
br_opt_get(br, BROPT_MULTICAST_ENABLED)) ||
nla_put_u8(skb, IFLA_BR_MCAST_QUERY_USE_IFADDR,
- br->multicast_query_use_ifaddr) ||
- nla_put_u8(skb, IFLA_BR_MCAST_QUERIER, br->multicast_querier) ||
+ br_opt_get(br, BROPT_MULTICAST_QUERY_USE_IFADDR)) ||
+ nla_put_u8(skb, IFLA_BR_MCAST_QUERIER,
+ br_opt_get(br, BROPT_MULTICAST_QUERIER)) ||
nla_put_u8(skb, IFLA_BR_MCAST_STATS_ENABLED,
- br->multicast_stats_enabled) ||
+ br_opt_get(br, BROPT_MULTICAST_STATS_ENABLED)) ||
nla_put_u32(skb, IFLA_BR_MCAST_HASH_ELASTICITY,
br->hash_elasticity) ||
nla_put_u32(skb, IFLA_BR_MCAST_HASH_MAX, br->hash_max) ||
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index fb1a266cdac8..e6bdb107fe04 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -314,6 +314,10 @@ enum net_bridge_opts {
BROPT_NF_CALL_ARPTABLES,
BROPT_GROUP_ADDR_SET,
BROPT_MULTICAST_ENABLED,
+ BROPT_MULTICAST_QUERIER,
+ BROPT_MULTICAST_QUERY_USE_IFADDR,
+ BROPT_MULTICAST_STATS_ENABLED,
+ BROPT_HAS_IPV6_ADDR,
};
struct net_bridge {
@@ -365,12 +369,6 @@ struct net_bridge {
} stp_enabled;
#ifdef CONFIG_BRIDGE_IGMP_SNOOPING
- unsigned char multicast_router;
-
- u8 multicast_querier:1;
- u8 multicast_query_use_ifaddr:1;
- u8 has_ipv6_addr:1;
- u8 multicast_stats_enabled:1;
u32 hash_elasticity;
u32 hash_max;
@@ -379,7 +377,10 @@ struct net_bridge {
u32 multicast_startup_query_count;
u8 multicast_igmp_version;
-
+ u8 multicast_router;
+#if IS_ENABLED(CONFIG_IPV6)
+ u8 multicast_mld_version;
+#endif
unsigned long multicast_last_member_interval;
unsigned long multicast_membership_interval;
unsigned long multicast_querier_interval;
@@ -400,7 +401,6 @@ struct net_bridge {
struct bridge_mcast_other_query ip6_other_query;
struct bridge_mcast_own_query ip6_own_query;
struct bridge_mcast_querier ip6_querier;
- u8 multicast_mld_version;
#endif /* IS_ENABLED(CONFIG_IPV6) */
#endif
@@ -707,8 +707,8 @@ __br_multicast_querier_exists(struct net_bridge *br,
{
bool own_querier_enabled;
- if (br->multicast_querier) {
- if (is_ipv6 && !br->has_ipv6_addr)
+ if (br_opt_get(br, BROPT_MULTICAST_QUERIER)) {
+ if (is_ipv6 && !br_opt_get(br, BROPT_HAS_IPV6_ADDR))
own_querier_enabled = false;
else
own_querier_enabled = true;
diff --git a/net/bridge/br_sysfs_br.c b/net/bridge/br_sysfs_br.c
index bf6f409a83e1..c93c5724609e 100644
--- a/net/bridge/br_sysfs_br.c
+++ b/net/bridge/br_sysfs_br.c
@@ -365,12 +365,13 @@ static ssize_t multicast_query_use_ifaddr_show(struct device *d,
char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%d\n", br->multicast_query_use_ifaddr);
+ return sprintf(buf, "%d\n",
+ br_opt_get(br, BROPT_MULTICAST_QUERY_USE_IFADDR));
}
static int set_query_use_ifaddr(struct net_bridge *br, unsigned long val)
{
- br->multicast_query_use_ifaddr = !!val;
+ br_opt_toggle(br, BROPT_MULTICAST_QUERY_USE_IFADDR, !!val);
return 0;
}
@@ -388,7 +389,7 @@ static ssize_t multicast_querier_show(struct device *d,
char *buf)
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%d\n", br->multicast_querier);
+ return sprintf(buf, "%d\n", br_opt_get(br, BROPT_MULTICAST_QUERIER));
}
static ssize_t multicast_querier_store(struct device *d,
@@ -636,12 +637,13 @@ static ssize_t multicast_stats_enabled_show(struct device *d,
{
struct net_bridge *br = to_bridge(d);
- return sprintf(buf, "%u\n", br->multicast_stats_enabled);
+ return sprintf(buf, "%d\n",
+ br_opt_get(br, BROPT_MULTICAST_STATS_ENABLED));
}
static int set_stats_enabled(struct net_bridge *br, unsigned long val)
{
- br->multicast_stats_enabled = !!val;
+ br_opt_toggle(br, BROPT_MULTICAST_STATS_ENABLED, !!val);
return 0;
}
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 7/9] net: bridge: convert neigh_suppress_enabled option to a bit
From: Nikolay Aleksandrov @ 2018-09-26 12:18 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
Convert the neigh_suppress_enabled option to a bit.
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_arp_nd_proxy.c | 13 ++++++++-----
net/bridge/br_device.c | 4 ++--
net/bridge/br_input.c | 2 +-
net/bridge/br_private.h | 2 +-
4 files changed, 12 insertions(+), 9 deletions(-)
diff --git a/net/bridge/br_arp_nd_proxy.c b/net/bridge/br_arp_nd_proxy.c
index d42e3904b498..6b78e6351719 100644
--- a/net/bridge/br_arp_nd_proxy.c
+++ b/net/bridge/br_arp_nd_proxy.c
@@ -39,7 +39,7 @@ void br_recalculate_neigh_suppress_enabled(struct net_bridge *br)
}
}
- br->neigh_suppress_enabled = neigh_suppress;
+ br_opt_toggle(br, BROPT_NEIGH_SUPPRESS_ENABLED, neigh_suppress);
}
#if IS_ENABLED(CONFIG_INET)
@@ -155,7 +155,7 @@ void br_do_proxy_suppress_arp(struct sk_buff *skb, struct net_bridge *br,
ipv4_is_multicast(tip))
return;
- if (br->neigh_suppress_enabled) {
+ if (br_opt_get(br, BROPT_NEIGH_SUPPRESS_ENABLED)) {
if (p && (p->flags & BR_NEIGH_SUPPRESS))
return;
if (ipv4_is_zeronet(sip) || sip == tip) {
@@ -175,7 +175,8 @@ void br_do_proxy_suppress_arp(struct sk_buff *skb, struct net_bridge *br,
return;
}
- if (br->neigh_suppress_enabled && br_is_local_ip(vlandev, tip)) {
+ if (br_opt_get(br, BROPT_NEIGH_SUPPRESS_ENABLED) &&
+ br_is_local_ip(vlandev, tip)) {
/* its our local ip, so don't proxy reply
* and don't forward to neigh suppress ports
*/
@@ -213,7 +214,8 @@ void br_do_proxy_suppress_arp(struct sk_buff *skb, struct net_bridge *br,
/* If we have replied or as long as we know the
* mac, indicate to arp replied
*/
- if (replied || br->neigh_suppress_enabled)
+ if (replied ||
+ br_opt_get(br, BROPT_NEIGH_SUPPRESS_ENABLED))
BR_INPUT_SKB_CB(skb)->proxyarp_replied = true;
}
@@ -460,7 +462,8 @@ void br_do_suppress_nd(struct sk_buff *skb, struct net_bridge *br,
* mac, indicate to NEIGH_SUPPRESS ports that we
* have replied
*/
- if (replied || br->neigh_suppress_enabled)
+ if (replied ||
+ br_opt_get(br, BROPT_NEIGH_SUPPRESS_ENABLED))
BR_INPUT_SKB_CB(skb)->proxyarp_replied = true;
}
neigh_release(n);
diff --git a/net/bridge/br_device.c b/net/bridge/br_device.c
index e682a668ce57..a0afdca73d8f 100644
--- a/net/bridge/br_device.c
+++ b/net/bridge/br_device.c
@@ -67,11 +67,11 @@ netdev_tx_t br_dev_xmit(struct sk_buff *skb, struct net_device *dev)
if (IS_ENABLED(CONFIG_INET) &&
(eth->h_proto == htons(ETH_P_ARP) ||
eth->h_proto == htons(ETH_P_RARP)) &&
- br->neigh_suppress_enabled) {
+ br_opt_get(br, BROPT_NEIGH_SUPPRESS_ENABLED)) {
br_do_proxy_suppress_arp(skb, br, vid, NULL);
} else if (IS_ENABLED(CONFIG_IPV6) &&
skb->protocol == htons(ETH_P_IPV6) &&
- br->neigh_suppress_enabled &&
+ br_opt_get(br, BROPT_NEIGH_SUPPRESS_ENABLED) &&
pskb_may_pull(skb, sizeof(struct ipv6hdr) +
sizeof(struct nd_msg)) &&
ipv6_hdr(skb)->nexthdr == IPPROTO_ICMPV6) {
diff --git a/net/bridge/br_input.c b/net/bridge/br_input.c
index 72074276c088..3ddca11f44c2 100644
--- a/net/bridge/br_input.c
+++ b/net/bridge/br_input.c
@@ -122,7 +122,7 @@ int br_handle_frame_finish(struct net *net, struct sock *sk, struct sk_buff *skb
br_do_proxy_suppress_arp(skb, br, vid, p);
} else if (IS_ENABLED(CONFIG_IPV6) &&
skb->protocol == htons(ETH_P_IPV6) &&
- br->neigh_suppress_enabled &&
+ br_opt_get(br, BROPT_NEIGH_SUPPRESS_ENABLED) &&
pskb_may_pull(skb, sizeof(struct ipv6hdr) +
sizeof(struct nd_msg)) &&
ipv6_hdr(skb)->nexthdr == IPPROTO_ICMPV6) {
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index e6bdb107fe04..6bdcc701bc71 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -318,6 +318,7 @@ enum net_bridge_opts {
BROPT_MULTICAST_QUERY_USE_IFADDR,
BROPT_MULTICAST_STATS_ENABLED,
BROPT_HAS_IPV6_ADDR,
+ BROPT_NEIGH_SUPPRESS_ENABLED,
};
struct net_bridge {
@@ -414,7 +415,6 @@ struct net_bridge {
#ifdef CONFIG_NET_SWITCHDEV
int offload_fwd_mark;
#endif
- bool neigh_suppress_enabled;
bool mtu_set_by_user;
struct hlist_head fdb_list;
};
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 8/9] net: bridge: convert mtu_set_by_user to a bit
From: Nikolay Aleksandrov @ 2018-09-26 12:18 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
Convert the last remaining bool option to a bit thus reducing the overall
net_bridge size further by 8 bytes.
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_device.c | 2 +-
net/bridge/br_if.c | 4 ++--
net/bridge/br_private.h | 2 +-
3 files changed, 4 insertions(+), 4 deletions(-)
diff --git a/net/bridge/br_device.c b/net/bridge/br_device.c
index a0afdca73d8f..e053a4e43758 100644
--- a/net/bridge/br_device.c
+++ b/net/bridge/br_device.c
@@ -228,7 +228,7 @@ static int br_change_mtu(struct net_device *dev, int new_mtu)
dev->mtu = new_mtu;
/* this flag will be cleared if the MTU was automatically adjusted */
- br->mtu_set_by_user = true;
+ br_opt_toggle(br, BROPT_MTU_SET_BY_USER, true);
#if IS_ENABLED(CONFIG_BRIDGE_NETFILTER)
/* remember the MTU in the rtable for PMTU */
dst_metric_set(&br->fake_rtable.dst, RTAX_MTU, new_mtu);
diff --git a/net/bridge/br_if.c b/net/bridge/br_if.c
index 3bb66508f07d..9b46d2dc4c22 100644
--- a/net/bridge/br_if.c
+++ b/net/bridge/br_if.c
@@ -508,14 +508,14 @@ void br_mtu_auto_adjust(struct net_bridge *br)
ASSERT_RTNL();
/* if the bridge MTU was manually configured don't mess with it */
- if (br->mtu_set_by_user)
+ if (br_opt_get(br, BROPT_MTU_SET_BY_USER))
return;
/* change to the minimum MTU and clear the flag which was set by
* the bridge ndo_change_mtu callback
*/
dev_set_mtu(br->dev, br_mtu_min(br));
- br->mtu_set_by_user = false;
+ br_opt_toggle(br, BROPT_MTU_SET_BY_USER, false);
}
static void br_set_gso_limits(struct net_bridge *br)
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index 6bdcc701bc71..92d08f8c7dd4 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -319,6 +319,7 @@ enum net_bridge_opts {
BROPT_MULTICAST_STATS_ENABLED,
BROPT_HAS_IPV6_ADDR,
BROPT_NEIGH_SUPPRESS_ENABLED,
+ BROPT_MTU_SET_BY_USER,
};
struct net_bridge {
@@ -415,7 +416,6 @@ struct net_bridge {
#ifdef CONFIG_NET_SWITCHDEV
int offload_fwd_mark;
#endif
- bool mtu_set_by_user;
struct hlist_head fdb_list;
};
--
2.11.0
^ permalink raw reply related
* [PATCH net-next 9/9] net: bridge: pack net_bridge better
From: Nikolay Aleksandrov @ 2018-09-26 12:18 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, Nikolay Aleksandrov
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
Further reduce the size of net_bridge with 8 bytes and reduce the number of
holes in it:
Before: holes: 5, sum holes: 15
After: holes: 2, sum holes: 3
Also as a bonus we get offload_fwd_mark in the first cache line and remove
the need to pull the last cache line of net_bridge just for that member in
fast path (should_deliver -> nbp_switchdev_allowed_egress).
Signed-off-by: Nikolay Aleksandrov <nikolay@cumulusnetworks.com>
---
net/bridge/br_private.h | 12 ++++++------
1 file changed, 6 insertions(+), 6 deletions(-)
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index 92d08f8c7dd4..e50506225666 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -329,6 +329,9 @@ struct net_bridge {
struct net_device *dev;
struct pcpu_sw_netstats __percpu *stats;
unsigned long options;
+#ifdef CONFIG_NET_SWITCHDEV
+ int offload_fwd_mark;
+#endif
/* These fields are accessed on each packet */
#ifdef CONFIG_BRIDGE_VLAN_FILTERING
__be16 vlan_proto;
@@ -349,7 +352,6 @@ struct net_bridge {
/* STP */
bridge_id designated_root;
bridge_id bridge_id;
- u32 root_path_cost;
unsigned char topology_change;
unsigned char topology_change_detected;
u16 root_port;
@@ -361,6 +363,7 @@ struct net_bridge {
unsigned long bridge_hello_time;
unsigned long bridge_forward_delay;
unsigned long bridge_ageing_time;
+ u32 root_path_cost;
u8 group_addr[ETH_ALEN];
@@ -383,6 +386,7 @@ struct net_bridge {
#if IS_ENABLED(CONFIG_IPV6)
u8 multicast_mld_version;
#endif
+ spinlock_t multicast_lock;
unsigned long multicast_last_member_interval;
unsigned long multicast_membership_interval;
unsigned long multicast_querier_interval;
@@ -390,7 +394,6 @@ struct net_bridge {
unsigned long multicast_query_response_interval;
unsigned long multicast_startup_query_interval;
- spinlock_t multicast_lock;
struct net_bridge_mdb_htable __rcu *mdb;
struct hlist_head router_list;
@@ -411,12 +414,9 @@ struct net_bridge {
struct timer_list topology_change_timer;
struct delayed_work gc_work;
struct kobject *ifobj;
- u32 auto_cnt;
-#ifdef CONFIG_NET_SWITCHDEV
- int offload_fwd_mark;
-#endif
struct hlist_head fdb_list;
+ u32 auto_cnt;
};
struct br_input_skb_cb {
--
2.11.0
^ permalink raw reply related
* Re: [PATCH net] dt-bindings: net: add support for Microchip KSZ9131 Ethernet PHY
From: Florian Fainelli @ 2018-09-26 18:33 UTC (permalink / raw)
To: Yuiko Oshino, davem, robh+dt, devicetree
Cc: linux-kernel, mark.rutland, m.felsch, Markus.Niebel, andrew,
netdev, UNGLinuxDriver
In-Reply-To: <1537985783-22724-1-git-send-email-yuiko.oshino@microchip.com>
On 09/26/2018 11:16 AM, Yuiko Oshino wrote:
> Add support for Microchip Technology KSZ9131 10/100/1000 Ethernet phy
Capitalize PHY here.
Targeting the "net" tree which is for bugfixes is not appropriate here
since this is adding support for a new PHY model.
The binding looks reasonable though:
Reviewed-by: Florian Fainelli <f.fainelli@gmail.com>
>
> Signed-off-by: Yuiko Oshino <yuiko.oshino@microchip.com>
> ---
> .../devicetree/bindings/net/micrel-ksz90x1.txt | 29 +++++++++++++++++++++-
> 1 file changed, 28 insertions(+), 1 deletion(-)
>
> diff --git a/Documentation/devicetree/bindings/net/micrel-ksz90x1.txt b/Documentation/devicetree/bindings/net/micrel-ksz90x1.txt
> index e22d8cf..d23d14a 100644
> --- a/Documentation/devicetree/bindings/net/micrel-ksz90x1.txt
> +++ b/Documentation/devicetree/bindings/net/micrel-ksz90x1.txt
> @@ -1,4 +1,4 @@
> -Micrel KSZ9021/KSZ9031 Gigabit Ethernet PHY
> +Micrel/Microchip KSZ9021/KSZ9031/KSZ9131 Gigabit Ethernet PHY
>
> Some boards require special tuning values, particularly when it comes
> to clock delays. You can specify clock delay values in the PHY OF
> @@ -64,6 +64,33 @@ KSZ9031:
> Attention: The link partner must be configurable as slave otherwise
> no link will be established.
>
> +KSZ9131:
> +
> + All skew control options are specified in picoseconds. The minimum
> + value is 0, and the maximum is property-dependent. The increment
> + step is 100ps. The default value is the neutral setting, so setting
> + rxc-skew-ps=<0> actually results in -700 picoseconds adjustment.
> +
> + Optional properties:
> +
> + Maximum value of 2400, default value 700:
> +
> + - rxc-skew-ps : Skew control of RX clock pad
> + - txc-skew-ps : Skew control of TX clock pad
> +
> + Maximum value of 1500, default value 700:
> +
> + - rxdv-skew-ps : Skew control of RX CTL pad
> + - txen-skew-ps : Skew control of TX CTL pad
> + - rxd0-skew-ps : Skew control of RX data 0 pad
> + - rxd1-skew-ps : Skew control of RX data 1 pad
> + - rxd2-skew-ps : Skew control of RX data 2 pad
> + - rxd3-skew-ps : Skew control of RX data 3 pad
> + - txd0-skew-ps : Skew control of TX data 0 pad
> + - txd1-skew-ps : Skew control of TX data 1 pad
> + - txd2-skew-ps : Skew control of TX data 2 pad
> + - txd3-skew-ps : Skew control of TX data 3 pad
> +
> Examples:
>
> mdio {
>
--
Florian
^ permalink raw reply
* Re: [PATCH 2/2] can: tcan4x5x: Add tcan4x5x driver to the kernel
From: Wolfgang Grandegger @ 2018-09-26 18:34 UTC (permalink / raw)
To: Dan Murphy, mkl, davem; +Cc: linux-can, netdev, linux-kernel
In-Reply-To: <4c9396a4-4028-f013-b22b-a181ef4278c7@ti.com>
Hello Dan,
Am 26.09.2018 um 20:00 schrieb Dan Murphy:
> Wolfgang
>
> On 09/26/2018 12:54 PM, Wolfgang Grandegger wrote:
>> Hello,
>>
>> I wonder why you do not extend the existing MCAN driver by implementing
>> an interface to access the hardware. Would that be feasible?
>>
>
> That did cross my mind. The issue is I have no way of testing the existing
> driver to make sure I did not break anything.
Yes, I can imagine, but we should try to avoid duplicated code in the
first place. I personally do not have a MCAN device at hand either, but
we should be able to manage that.
> My thought was to create a basic MCAN framework and attach the devices to it.
> So, like in this case, if there is a special way to talk to the device it can
> be handled in the device driver.
Basically, that's what I have in mind. The "mcan" driver uses it's own
directory with just one file in it. Maybe the idea behind that was to
extend it sooner than later like the "c_can" driver.
> If thats what is needed then I will have to re-write the driver.
Let's have a closer look first. If it's just about accessing one
register at a time, like with memory mapped io, the interface should be
trivial but with SPI we may want to read/write a bulk of data to speed
up the register accesses, use a work queue or thread, etc.
Wolfgang
^ permalink raw reply
* Re: [PATCH net] net: phy: micrel: add Microchip KSZ9131 inital driver
From: Florian Fainelli @ 2018-09-26 18:34 UTC (permalink / raw)
To: Yuiko Oshino, andrew, davem, netdev, linux-kernel; +Cc: UNGLinuxDriver
In-Reply-To: <1537986141-22832-1-git-send-email-yuiko.oshino@microchip.com>
On 09/26/2018 11:22 AM, Yuiko Oshino wrote:
> Add support for Microchip Technology KSZ9131 10/100/1000 Ethernet phy
>
> Signed-off-by: Yuiko Oshino <yuiko.oshino@microchip.com>
Reviewed-by: Florian Fainelli <f.fainelli@gmail.com>
Same as the previous patch, targeting the "net" tree is not appropriate
here.
Since the two patches are obviously linked, you might consider adding a
cover letter to introduce them.
Thanks!
--
Florian
^ permalink raw reply
* Re: [PATCH] net: nixge: fix warnings on 32-bit platforms
From: Arnd Bergmann @ 2018-09-26 18:47 UTC (permalink / raw)
To: mdf; +Cc: David Miller, Networking, Linux Kernel Mailing List
In-Reply-To: <20180926160328.GA1927@archbook>
On Wed, Sep 26, 2018 at 6:03 PM Moritz Fischer <mdf@kernel.org> wrote:
>
> Hi Arnd,
>
> On Wed, Sep 26, 2018 at 02:47:24PM +0200, Arnd Bergmann wrote:
> > Making it work on 64-bit caused 32-bit builds to regress:
> >
>
> I had submitted a similar patch https://lkml.org/lkml/2018/9/24/1719
> here. I should probably add the Fixes tag yours has but other than that
> they look largely equivalent. Comments?
Yes, I'm sure your version is fine as well, sorry for missing that.
Adding a fixes tag is generally a good idea, but no need to resend it.
We just need one of the two to get picked up into net-next.
[note: we both forgot to tag the patch as "[PATCH net-next]"]
Arnd
^ permalink raw reply
* Re: [PATCH net-next] net/core: make function ___gnet_stats_copy_basic() static
From: Eelco Chaudron @ 2018-09-26 12:38 UTC (permalink / raw)
To: Wei Yongjun; +Cc: john.fastabend, toke, netdev, kernel-janitors
In-Reply-To: <1537963785-165570-1-git-send-email-weiyongjun1@huawei.com>
On 26 Sep 2018, at 14:09, Wei Yongjun wrote:
> Fixes the following sparse warning:
>
> net/core/gen_stats.c:166:1: warning:
> symbol '___gnet_stats_copy_basic' was not declared. Should it be static?
>
Thanks for fixing my commit ;)
Acked-by: Eelco Chaudron <echaudro@redhat.com>
> Fixes: 5e111210a443 ("net/core: Add new basic hardware counter")
> Signed-off-by: Wei Yongjun <weiyongjun1@huawei.com>
> ---
> net/core/gen_stats.c | 2 +-
> 1 file changed, 1 insertion(+), 1 deletion(-)
>
> diff --git a/net/core/gen_stats.c b/net/core/gen_stats.c
> index 65a2e82..9bf1b9a 100644
> --- a/net/core/gen_stats.c
> +++ b/net/core/gen_stats.c
> @@ -162,7 +162,7 @@
> }
> EXPORT_SYMBOL(__gnet_stats_copy_basic);
>
> -int
> +static int
> ___gnet_stats_copy_basic(const seqcount_t *running,
> struct gnet_dump *d,
> struct gnet_stats_basic_cpu __percpu *cpu,
^ permalink raw reply
* Re: [PATCH net-next 0/9] net: bridge: convert bool options to bits
From: Stephen Hemminger @ 2018-09-26 12:52 UTC (permalink / raw)
To: Nikolay Aleksandrov; +Cc: netdev, roopa, davem, bridge
In-Reply-To: <20180926121802.27851-1-nikolay@cumulusnetworks.com>
On Wed, 26 Sep 2018 15:17:53 +0300
Nikolay Aleksandrov <nikolay@cumulusnetworks.com> wrote:
> Hi,
> A lot of boolean bridge options have been added around the net_bridge
> structure resulting in holes and more importantly different cache lines
> that need to be fetched in the fast path. This set moves all of those
> to bits in a bitfield which resides in a hot cache line thus reducing
> the size of net_bridge, the number of holes and the number of cache
> lines needed for the fast path.
> The set is also sent in preparation for new boolean options to avoid
> spreading them in the structure and making new holes.
> One nice side-effect is that we avoid potential race conditions by using
> the bitops since some of the options were bits being directly set in
> parallel risking hard to debug issues (has_ipv6_addr).
>
> Before:
> size: 1184, holes: 8, sum holes: 30
> After:
> size: 1160, holes: 2, sum holes: 3
>
> Patch 01 is a trivial style fix
> Patch 02 adds the new options bitfield and converts the vlan boolean
> options to bits
> Patches 03-08 convert the rest of the boolean options to bits
> Patch 09 re-arranges a few fields in net_bridge to avoid fetching one
> extra cache line in fast path and to further reduce size
>
> Thanks,
> Nik
>
>
> Nikolay Aleksandrov (9):
> net: bridge: make struct opening bracket consistent
> net: bridge: add bitfield for options and convert vlan opts
> net: bridge: convert nf call options to bits
> net: bridge: convert group_addr_set option to a bit
> net: bridge: convert and rename mcast disabled
> net: bridge: convert mcast options to bits
> net: bridge: convert neigh_suppress_enabled option to a bit
> net: bridge: convert mtu_set_by_user to a bit
> net: bridge: pack net_bridge better
>
> net/bridge/br.c | 16 +++++++++
> net/bridge/br_arp_nd_proxy.c | 13 +++++---
> net/bridge/br_device.c | 6 ++--
> net/bridge/br_if.c | 4 +--
> net/bridge/br_input.c | 2 +-
> net/bridge/br_mdb.c | 6 ++--
> net/bridge/br_multicast.c | 54 +++++++++++++++---------------
> net/bridge/br_netfilter_hooks.c | 7 ++--
> net/bridge/br_netlink.c | 31 +++++++++--------
> net/bridge/br_private.h | 74 +++++++++++++++++++++++------------------
> net/bridge/br_sysfs_br.c | 32 +++++++++---------
> net/bridge/br_vlan.c | 30 +++++++++--------
> 12 files changed, 155 insertions(+), 120 deletions(-)
>
Looks good, these flags grew over time and cleanup was overdue.
Reviewed-by: Stephen Hemminger <stephen@networkplumber.org>
^ permalink raw reply
* [PATCH v2 01/22] soc/fsl/qman: fixup liodns only on ppc targets
From: laurentiu.tudor @ 2018-09-26 13:22 UTC (permalink / raw)
To: devicetree, netdev, linux-kernel, linux-arm-kernel
Cc: roy.pledge, madalin.bucur, davem, shawnguo, leoyang.li,
robin.murphy, bharat.bhushan, Laurentiu Tudor
In-Reply-To: <20180926132247.10971-1-laurentiu.tudor@nxp.com>
From: Laurentiu Tudor <laurentiu.tudor@nxp.com>
ARM SoCs use SMMU so the liodn fixup done in the qman driver is no
longer making sense and it also breaks the ICID settings inherited
from u-boot. Do the fixups only for PPC targets.
Signed-off-by: Laurentiu Tudor <laurentiu.tudor@nxp.com>
---
drivers/soc/fsl/qbman/qman_ccsr.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/drivers/soc/fsl/qbman/qman_ccsr.c b/drivers/soc/fsl/qbman/qman_ccsr.c
index 79cba58387a5..619e22030460 100644
--- a/drivers/soc/fsl/qbman/qman_ccsr.c
+++ b/drivers/soc/fsl/qbman/qman_ccsr.c
@@ -597,6 +597,7 @@ static int qman_init_ccsr(struct device *dev)
#define LIO_CFG_LIODN_MASK 0x0fff0000
void qman_liodn_fixup(u16 channel)
{
+#ifdef CONFIG_PPC
static int done;
static u32 liodn_offset;
u32 before, after;
@@ -616,6 +617,7 @@ void qman_liodn_fixup(u16 channel)
qm_ccsr_out(REG_REV3_QCSP_LIO_CFG(idx), after);
else
qm_ccsr_out(REG_QCSP_LIO_CFG(idx), after);
+#endif
}
#define IO_CFG_SDEST_MASK 0x00ff0000
--
2.17.1
^ permalink raw reply related
* [PATCH v2 03/22] soc/fsl/qman: map FQD and PFDR areas in the iommu
From: laurentiu.tudor @ 2018-09-26 13:22 UTC (permalink / raw)
To: devicetree, netdev, linux-kernel, linux-arm-kernel
Cc: roy.pledge, madalin.bucur, davem, shawnguo, leoyang.li,
robin.murphy, bharat.bhushan, Laurentiu Tudor
In-Reply-To: <20180926132247.10971-1-laurentiu.tudor@nxp.com>
From: Laurentiu Tudor <laurentiu.tudor@nxp.com>
Add a one-to-one iommu mapping for qman private data memory areas
(FQD and PFDR). This is required for QMAN to work without faults
behind an iommu.
Signed-off-by: Laurentiu Tudor <laurentiu.tudor@nxp.com>
---
drivers/soc/fsl/qbman/qman_ccsr.c | 15 +++++++++++++++
1 file changed, 15 insertions(+)
diff --git a/drivers/soc/fsl/qbman/qman_ccsr.c b/drivers/soc/fsl/qbman/qman_ccsr.c
index 619e22030460..0cfe79f85a66 100644
--- a/drivers/soc/fsl/qbman/qman_ccsr.c
+++ b/drivers/soc/fsl/qbman/qman_ccsr.c
@@ -29,6 +29,7 @@
*/
#include "qman_priv.h"
+#include <linux/iommu.h>
u16 qman_ip_rev;
EXPORT_SYMBOL(qman_ip_rev);
@@ -692,6 +693,7 @@ static int fsl_qman_probe(struct platform_device *pdev)
{
struct device *dev = &pdev->dev;
struct device_node *node = dev->of_node;
+ struct iommu_domain *domain;
struct resource *res;
int ret, err_irq;
u16 id;
@@ -769,6 +771,19 @@ static int fsl_qman_probe(struct platform_device *pdev)
}
dev_dbg(dev, "Allocated PFDR 0x%llx 0x%zx\n", pfdr_a, pfdr_sz);
+ /* Create an 1-to-1 iommu mapping for fqd and pfdr areas */
+ domain = iommu_get_domain_for_dev(dev);
+ if (domain) {
+ ret = iommu_map(domain, fqd_a, fqd_a, fqd_sz,
+ IOMMU_READ | IOMMU_WRITE | IOMMU_CACHE);
+ if (ret)
+ dev_warn(dev, "iommu_map(fqd) failed %d\n", ret);
+ ret = iommu_map(domain, pfdr_a, pfdr_a, pfdr_sz,
+ IOMMU_READ | IOMMU_WRITE | IOMMU_CACHE);
+ if (ret)
+ dev_warn(dev, "iommu_map(pfdr) failed %d\n", ret);
+ }
+
ret = qman_init_ccsr(dev);
if (ret) {
dev_err(dev, "CCSR setup failed\n");
--
2.17.1
^ permalink raw reply related
* [PATCH v2 05/22] soc/fsl/qbman: add APIs to retrieve the probing status
From: laurentiu.tudor @ 2018-09-26 13:22 UTC (permalink / raw)
To: devicetree, netdev, linux-kernel, linux-arm-kernel
Cc: roy.pledge, madalin.bucur, davem, shawnguo, leoyang.li,
robin.murphy, bharat.bhushan, Laurentiu Tudor
In-Reply-To: <20180926132247.10971-1-laurentiu.tudor@nxp.com>
From: Laurentiu Tudor <laurentiu.tudor@nxp.com>
Add a couple of new APIs to check the probing status of qman and bman:
'int bman_is_probed()' and 'int qman_is_probed()'.
They return the following values.
* 1 if qman/bman were probed correctly
* 0 if qman/bman were not yet probed
* -1 if probing of qman/bman failed
Drivers that use qman/bman driver services are required to use these
APIs before calling any functions exported by qman or bman drivers
or otherwise they will crash the kernel.
The APIs will be used in the following couple of qbman portal patches
and later in the series in the dpaa1 ethernet driver.
Signed-off-by: Laurentiu Tudor <laurentiu.tudor@nxp.com>
---
drivers/soc/fsl/qbman/bman_ccsr.c | 11 +++++++++++
drivers/soc/fsl/qbman/qman_ccsr.c | 11 +++++++++++
include/soc/fsl/bman.h | 8 ++++++++
include/soc/fsl/qman.h | 8 ++++++++
4 files changed, 38 insertions(+)
diff --git a/drivers/soc/fsl/qbman/bman_ccsr.c b/drivers/soc/fsl/qbman/bman_ccsr.c
index d180da003e4a..b209c79511bb 100644
--- a/drivers/soc/fsl/qbman/bman_ccsr.c
+++ b/drivers/soc/fsl/qbman/bman_ccsr.c
@@ -121,6 +121,7 @@ static void bm_set_memory(u64 ba, u32 size)
*/
static dma_addr_t fbpr_a;
static size_t fbpr_sz;
+static int __bman_probed;
static int bman_fbpr(struct reserved_mem *rmem)
{
@@ -167,6 +168,12 @@ static irqreturn_t bman_isr(int irq, void *ptr)
return IRQ_HANDLED;
}
+int bman_is_probed(void)
+{
+ return __bman_probed;
+}
+EXPORT_SYMBOL_GPL(bman_is_probed);
+
static int fsl_bman_probe(struct platform_device *pdev)
{
int ret, err_irq;
@@ -177,6 +184,8 @@ static int fsl_bman_probe(struct platform_device *pdev)
u16 id, bm_pool_cnt;
u8 major, minor;
+ __bman_probed = -1;
+
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
if (!res) {
dev_err(dev, "Can't get %pOF property 'IORESOURCE_MEM'\n",
@@ -266,6 +275,8 @@ static int fsl_bman_probe(struct platform_device *pdev)
return ret;
}
+ __bman_probed = 1;
+
return 0;
};
diff --git a/drivers/soc/fsl/qbman/qman_ccsr.c b/drivers/soc/fsl/qbman/qman_ccsr.c
index 0cfe79f85a66..383a49dcce68 100644
--- a/drivers/soc/fsl/qbman/qman_ccsr.c
+++ b/drivers/soc/fsl/qbman/qman_ccsr.c
@@ -274,6 +274,7 @@ static const struct qman_error_info_mdata error_mdata[] = {
static u32 __iomem *qm_ccsr_start;
/* A SDQCR mask comprising all the available/visible pool channels */
static u32 qm_pools_sdqcr;
+static int __qman_probed;
static inline u32 qm_ccsr_in(u32 offset)
{
@@ -689,6 +690,12 @@ static int qman_resource_init(struct device *dev)
return 0;
}
+int qman_is_probed(void)
+{
+ return __qman_probed;
+}
+EXPORT_SYMBOL_GPL(qman_is_probed);
+
static int fsl_qman_probe(struct platform_device *pdev)
{
struct device *dev = &pdev->dev;
@@ -699,6 +706,8 @@ static int fsl_qman_probe(struct platform_device *pdev)
u16 id;
u8 major, minor;
+ __qman_probed = -1;
+
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
if (!res) {
dev_err(dev, "Can't get %pOF property 'IORESOURCE_MEM'\n",
@@ -845,6 +854,8 @@ static int fsl_qman_probe(struct platform_device *pdev)
if (ret)
return ret;
+ __qman_probed = 1;
+
return 0;
}
diff --git a/include/soc/fsl/bman.h b/include/soc/fsl/bman.h
index eaaf56df4086..5b99cb2ea5ef 100644
--- a/include/soc/fsl/bman.h
+++ b/include/soc/fsl/bman.h
@@ -126,4 +126,12 @@ int bman_release(struct bman_pool *pool, const struct bm_buffer *bufs, u8 num);
*/
int bman_acquire(struct bman_pool *pool, struct bm_buffer *bufs, u8 num);
+/**
+ * bman_is_probed - Check if bman is probed
+ *
+ * Returns 1 if the bman driver successfully probed, -1 if the bman driver
+ * failed to probe or 0 if the bman driver did not probed yet.
+ */
+int bman_is_probed(void);
+
#endif /* __FSL_BMAN_H */
diff --git a/include/soc/fsl/qman.h b/include/soc/fsl/qman.h
index d4dfefdee6c1..597783b8a3a0 100644
--- a/include/soc/fsl/qman.h
+++ b/include/soc/fsl/qman.h
@@ -1186,4 +1186,12 @@ int qman_alloc_cgrid_range(u32 *result, u32 count);
*/
int qman_release_cgrid(u32 id);
+/**
+ * qman_is_probed - Check if qman is probed
+ *
+ * Returns 1 if the qman driver successfully probed, -1 if the qman driver
+ * failed to probe or 0 if the qman driver did not probed yet.
+ */
+int qman_is_probed(void);
+
#endif /* __FSL_QMAN_H */
--
2.17.1
^ permalink raw reply related
* [PATCH v2 07/22] soc/fsl/bman_portals: defer probe after bman's probe
From: laurentiu.tudor @ 2018-09-26 13:22 UTC (permalink / raw)
To: devicetree, netdev, linux-kernel, linux-arm-kernel
Cc: roy.pledge, madalin.bucur, davem, shawnguo, leoyang.li,
robin.murphy, bharat.bhushan, Laurentiu Tudor
In-Reply-To: <20180926132247.10971-1-laurentiu.tudor@nxp.com>
From: Laurentiu Tudor <laurentiu.tudor@nxp.com>
A crash in bman portal probing could not be triggered (as is the case
with qman portals) but it does make calls [1] into the bman driver so
lets make sure the bman portal probing happens after bman's.
[1] bman_p_irqsource_add() (in bman) called by:
init_pcfg() called by:
bman_portal_probe()
Signed-off-by: Laurentiu Tudor <laurentiu.tudor@nxp.com>
---
drivers/soc/fsl/qbman/bman_portal.c | 10 +++++++++-
1 file changed, 9 insertions(+), 1 deletion(-)
diff --git a/drivers/soc/fsl/qbman/bman_portal.c b/drivers/soc/fsl/qbman/bman_portal.c
index 2f71f7df3465..f9edd28894fd 100644
--- a/drivers/soc/fsl/qbman/bman_portal.c
+++ b/drivers/soc/fsl/qbman/bman_portal.c
@@ -91,7 +91,15 @@ static int bman_portal_probe(struct platform_device *pdev)
struct device_node *node = dev->of_node;
struct bm_portal_config *pcfg;
struct resource *addr_phys[2];
- int irq, cpu;
+ int irq, cpu, err;
+
+ err = bman_is_probed();
+ if (!err)
+ return -EPROBE_DEFER;
+ if (err < 0) {
+ dev_err(&pdev->dev, "failing probe due to bman probe error\n");
+ return -ENODEV;
+ }
pcfg = devm_kmalloc(dev, sizeof(*pcfg), GFP_KERNEL);
if (!pcfg)
--
2.17.1
^ permalink raw reply related
* Re: [PATCH net-next 9/9] net: bridge: pack net_bridge better
From: Ido Schimmel @ 2018-09-26 13:30 UTC (permalink / raw)
To: Nikolay Aleksandrov; +Cc: netdev, roopa, davem, stephen, bridge
In-Reply-To: <20180926121802.27851-10-nikolay@cumulusnetworks.com>
On Wed, Sep 26, 2018 at 03:18:02PM +0300, Nikolay Aleksandrov wrote:
> Further reduce the size of net_bridge with 8 bytes and reduce the number of
> holes in it:
> Before: holes: 5, sum holes: 15
> After: holes: 2, sum holes: 3
>
> Also as a bonus we get offload_fwd_mark in the first cache line and remove
> the need to pull the last cache line of net_bridge just for that member in
> fast path (should_deliver -> nbp_switchdev_allowed_egress).
But nbp_switchdev_allowed_egress() compares with 'offload_fwd_mark' from
'net_bridge_port', not 'net_bridge'...
^ permalink raw reply
* Re: [PATCH net-next 9/9] net: bridge: pack net_bridge better
From: Nikolay Aleksandrov @ 2018-09-26 13:35 UTC (permalink / raw)
To: Ido Schimmel; +Cc: netdev, roopa, davem, stephen, bridge
In-Reply-To: <20180926133014.GA31563@splinter>
On 26/09/18 16:30, Ido Schimmel wrote:
> On Wed, Sep 26, 2018 at 03:18:02PM +0300, Nikolay Aleksandrov wrote:
>> Further reduce the size of net_bridge with 8 bytes and reduce the number of
>> holes in it:
>> Before: holes: 5, sum holes: 15
>> After: holes: 2, sum holes: 3
>>
>> Also as a bonus we get offload_fwd_mark in the first cache line and remove
>> the need to pull the last cache line of net_bridge just for that member in
>> fast path (should_deliver -> nbp_switchdev_allowed_egress).
>
> But nbp_switchdev_allowed_egress() compares with 'offload_fwd_mark' from
> 'net_bridge_port', not 'net_bridge'...
>
ha, right you are! I need to check my glasses :) Anyway, I'll correct my
commit message and resend v2. We can leave the net_bridge mark in the
end, there're 4 bytes there anyway.
I was thinking of net_bridge_port, but that is a different patch-set I
have. Apparently I've mixed the commit messages.
Thanks!
^ permalink raw reply
* [PATCH] netlink: add policy attribute range validation
From: Johannes Berg @ 2018-09-26 20:06 UTC (permalink / raw)
To: linux-wireless-u79uwXL29TY76Z2rM5mHXA,
netdev-u79uwXL29TY76Z2rM5mHXA
Cc: Johannes Berg
From: Johannes Berg <johannes.berg-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org>
Without further bloating the policy structs, we can overload
the `validation_data' pointer with a struct of s16 min, max
and use those to validate ranges in NLA_{U,S}{8,16,32,64}
attributes.
It may sound strange to validate NLA_U32 with a s16 max, but
in many cases NLA_U32 is used for enums etc. since there's no
size benefit in using a smaller attribute width anyway, due
to netlink attribute alignment; in cases like that it's still
useful, particularly when the attribute really transports an
enum value.
Doing so lets us remove quite a bit of validation code, if we
can be sure that these attributes aren't used by userspace in
places where they're ignored today.
Signed-off-by: Johannes Berg <johannes.berg-ral2JQCrhuEAvxtiuMwx3w@public.gmane.org>
---
include/net/netlink.h | 25 +++++++++++++++++++++++--
lib/nlattr.c | 49 +++++++++++++++++++++++++++++++++++++++++++++++++
2 files changed, 72 insertions(+), 2 deletions(-)
diff --git a/include/net/netlink.h b/include/net/netlink.h
index 3698ca8ff92c..ddabc832febc 100644
--- a/include/net/netlink.h
+++ b/include/net/netlink.h
@@ -238,7 +238,23 @@ enum {
* nested attributes directly inside, while an array has
* the nested attributes at another level down and the
* attributes directly in the nesting don't matter.
- * All other Unused
+ * All other Unused - but note that it's a union
+ *
+ * Meaning of `min' and `max' fields:
+ * NLA_U8,
+ * NLA_U16,
+ * NLA_U32,
+ * NLA_U64,
+ * NLA_S8,
+ * NLA_S16,
+ * NLA_S32,
+ * NLA_S64 If at least one of them is non-zero, they are the
+ * minimum and maximum value accepted for the attribute;
+ * note that in the interest of code simplicity and
+ * struct size both limits are s16, so you cannot
+ * enforce a range that doesn't fall within the range
+ * of s16 - do that as usual in the code instead.
+ * All other Unused - but note that it's a union
*
* Example:
* static const struct nla_policy my_policy[ATTR_MAX+1] = {
@@ -251,7 +267,12 @@ enum {
struct nla_policy {
u16 type;
u16 len;
- const void *validation_data;
+ union {
+ const void *validation_data;
+ struct {
+ s16 min, max;
+ };
+ };
};
#define NLA_POLICY_EXACT_LEN(_len) { .type = NLA_EXACT_LEN, .len = _len }
diff --git a/lib/nlattr.c b/lib/nlattr.c
index 2f8feff669a7..dd8d34c1ae19 100644
--- a/lib/nlattr.c
+++ b/lib/nlattr.c
@@ -230,6 +230,55 @@ static int validate_nla(const struct nlattr *nla, int maxtype,
goto out_err;
}
+ /* validate range */
+ if (pt->min || pt->max) {
+ s64 value;
+ bool validate = true;
+
+ switch (pt->type) {
+ case NLA_U8:
+ value = nla_get_u8(nla);
+ break;
+ case NLA_U16:
+ value = nla_get_u16(nla);
+ break;
+ case NLA_U32:
+ value = nla_get_u32(nla);
+ break;
+ case NLA_S8:
+ value = nla_get_s8(nla);
+ break;
+ case NLA_S16:
+ value = nla_get_s16(nla);
+ break;
+ case NLA_S32:
+ value = nla_get_s32(nla);
+ break;
+ case NLA_S64:
+ value = nla_get_s64(nla);
+ break;
+ case NLA_U64:
+ /* treat this one specially, since it may not fit into s64 */
+ if (nla_get_u64(nla) < pt->min ||
+ nla_get_u64(nla) > pt->max) {
+ NL_SET_ERR_MSG_ATTR(extack, nla,
+ "integer out of range");
+ return -ERANGE;
+ }
+ /* fall through */
+ default:
+ /* no further validation */
+ validate = false;
+ break;
+ }
+
+ if (validate && (value < pt->min || value > pt->max)) {
+ NL_SET_ERR_MSG_ATTR(extack, nla,
+ "integer out of range");
+ return -ERANGE;
+ }
+ }
+
return 0;
out_err:
NL_SET_ERR_MSG_ATTR(extack, nla, "Attribute failed policy validation");
--
2.14.4
^ permalink raw reply related
* [PATCH net-next v2 0/9] net: bridge: convert bool options to bits
From: Nikolay Aleksandrov @ 2018-09-26 14:00 UTC (permalink / raw)
To: netdev; +Cc: roopa, davem, stephen, bridge, idosch, Nikolay Aleksandrov
Hi,
A lot of boolean bridge options have been added around the net_bridge
structure resulting in holes and more importantly different cache lines
that need to be fetched in the fast path. This set moves all of those
to bits in a bitfield which resides in a hot cache line thus reducing
the size of net_bridge, the number of holes and the number of cache
lines needed for the fast path.
The set is also sent in preparation for new boolean options to avoid
spreading them in the structure and making new holes.
One nice side-effect is that we avoid potential race conditions by using
the bitops since some of the options were bits being directly set in
parallel risking hard to debug issues (has_ipv6_addr).
Before:
size: 1184, holes: 8, sum holes: 30
After:
size: 1160, holes: 3, sum holes: 7
Patch 01 is a trivial style fix
Patch 02 adds the new options bitfield and converts the vlan boolean
options to bits
Patches 03-08 convert the rest of the boolean options to bits
Patch 09 re-arranges a few fields in net_bridge to further reduce size
v2: patch 09: remove the comment about offload_fwd_mark in net_bridge and
leave it in the last 4 bytes, thanks to Ido for spotting it
Stephen, I've added your reviewed-by in patches 01-08, only removed it
from patch 09 as the patch has changed.
Thanks,
Nik
Nikolay Aleksandrov (9):
net: bridge: make struct opening bracket consistent
net: bridge: add bitfield for options and convert vlan opts
net: bridge: convert nf call options to bits
net: bridge: convert group_addr_set option to a bit
net: bridge: convert and rename mcast disabled
net: bridge: convert mcast options to bits
net: bridge: convert neigh_suppress_enabled option to a bit
net: bridge: convert mtu_set_by_user to a bit
net: bridge: pack net_bridge better
net/bridge/br.c | 16 ++++++++++
net/bridge/br_arp_nd_proxy.c | 13 ++++----
net/bridge/br_device.c | 6 ++--
net/bridge/br_if.c | 4 +--
net/bridge/br_input.c | 2 +-
net/bridge/br_mdb.c | 6 ++--
net/bridge/br_multicast.c | 54 ++++++++++++++++-----------------
net/bridge/br_netfilter_hooks.c | 7 +++--
net/bridge/br_netlink.c | 31 ++++++++++---------
net/bridge/br_private.h | 66 +++++++++++++++++++++++------------------
net/bridge/br_sysfs_br.c | 32 ++++++++++----------
net/bridge/br_vlan.c | 30 ++++++++++---------
12 files changed, 151 insertions(+), 116 deletions(-)
--
2.11.0
^ permalink raw reply
page: next (older) | prev (newer) | latest
- recent:[subjects (threaded)|topics (new)|topics (active)]
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox