aboutsummaryrefslogtreecommitdiffstats
path: root/net/bridge
diff options
context:
space:
mode:
Diffstat (limited to 'net/bridge')
-rw-r--r--net/bridge/br_netlink.c6
-rw-r--r--net/bridge/br_private.h1
-rw-r--r--net/bridge/br_stp_bpdu.c7
-rw-r--r--net/bridge/br_sysfs_if.c2
4 files changed, 15 insertions, 1 deletions
diff --git a/net/bridge/br_netlink.c b/net/bridge/br_netlink.c
index 0188a2f706c4..c331e28c7880 100644
--- a/net/bridge/br_netlink.c
+++ b/net/bridge/br_netlink.c
@@ -26,6 +26,7 @@ static inline size_t br_port_info_size(void)
26 + nla_total_size(2) /* IFLA_BRPORT_PRIORITY */ 26 + nla_total_size(2) /* IFLA_BRPORT_PRIORITY */
27 + nla_total_size(4) /* IFLA_BRPORT_COST */ 27 + nla_total_size(4) /* IFLA_BRPORT_COST */
28 + nla_total_size(1) /* IFLA_BRPORT_MODE */ 28 + nla_total_size(1) /* IFLA_BRPORT_MODE */
29 + nla_total_size(1) /* IFLA_BRPORT_GUARD */
29 + 0; 30 + 0;
30} 31}
31 32
@@ -49,7 +50,8 @@ static int br_port_fill_attrs(struct sk_buff *skb,
49 if (nla_put_u8(skb, IFLA_BRPORT_STATE, p->state) || 50 if (nla_put_u8(skb, IFLA_BRPORT_STATE, p->state) ||
50 nla_put_u16(skb, IFLA_BRPORT_PRIORITY, p->priority) || 51 nla_put_u16(skb, IFLA_BRPORT_PRIORITY, p->priority) ||
51 nla_put_u32(skb, IFLA_BRPORT_COST, p->path_cost) || 52 nla_put_u32(skb, IFLA_BRPORT_COST, p->path_cost) ||
52 nla_put_u8(skb, IFLA_BRPORT_MODE, mode)) 53 nla_put_u8(skb, IFLA_BRPORT_MODE, mode) ||
54 nla_put_u8(skb, IFLA_BRPORT_GUARD, !!(p->flags & BR_BPDU_GUARD)))
53 return -EMSGSIZE; 55 return -EMSGSIZE;
54 56
55 return 0; 57 return 0;
@@ -162,6 +164,7 @@ static const struct nla_policy ifla_brport_policy[IFLA_BRPORT_MAX + 1] = {
162 [IFLA_BRPORT_COST] = { .type = NLA_U32 }, 164 [IFLA_BRPORT_COST] = { .type = NLA_U32 },
163 [IFLA_BRPORT_PRIORITY] = { .type = NLA_U16 }, 165 [IFLA_BRPORT_PRIORITY] = { .type = NLA_U16 },
164 [IFLA_BRPORT_MODE] = { .type = NLA_U8 }, 166 [IFLA_BRPORT_MODE] = { .type = NLA_U8 },
167 [IFLA_BRPORT_GUARD] = { .type = NLA_U8 },
165}; 168};
166 169
167/* Change the state of the port and notify spanning tree */ 170/* Change the state of the port and notify spanning tree */
@@ -203,6 +206,7 @@ static int br_setport(struct net_bridge_port *p, struct nlattr *tb[])
203 int err; 206 int err;
204 207
205 br_set_port_flag(p, tb, IFLA_BRPORT_MODE, BR_HAIRPIN_MODE); 208 br_set_port_flag(p, tb, IFLA_BRPORT_MODE, BR_HAIRPIN_MODE);
209 br_set_port_flag(p, tb, IFLA_BRPORT_GUARD, BR_BPDU_GUARD);
206 210
207 if (tb[IFLA_BRPORT_COST]) { 211 if (tb[IFLA_BRPORT_COST]) {
208 err = br_stp_set_path_cost(p, nla_get_u32(tb[IFLA_BRPORT_COST])); 212 err = br_stp_set_path_cost(p, nla_get_u32(tb[IFLA_BRPORT_COST]));
diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h
index 22111ffd68df..c92b0804ff2d 100644
--- a/net/bridge/br_private.h
+++ b/net/bridge/br_private.h
@@ -135,6 +135,7 @@ struct net_bridge_port
135 135
136 unsigned long flags; 136 unsigned long flags;
137#define BR_HAIRPIN_MODE 0x00000001 137#define BR_HAIRPIN_MODE 0x00000001
138#define BR_BPDU_GUARD 0x00000002
138 139
139#ifdef CONFIG_BRIDGE_IGMP_SNOOPING 140#ifdef CONFIG_BRIDGE_IGMP_SNOOPING
140 u32 multicast_startup_queries_sent; 141 u32 multicast_startup_queries_sent;
diff --git a/net/bridge/br_stp_bpdu.c b/net/bridge/br_stp_bpdu.c
index fd30a6022dea..7f884e3fb955 100644
--- a/net/bridge/br_stp_bpdu.c
+++ b/net/bridge/br_stp_bpdu.c
@@ -170,6 +170,13 @@ void br_stp_rcv(const struct stp_proto *proto, struct sk_buff *skb,
170 if (!ether_addr_equal(dest, br->group_addr)) 170 if (!ether_addr_equal(dest, br->group_addr))
171 goto out; 171 goto out;
172 172
173 if (p->flags & BR_BPDU_GUARD) {
174 br_notice(br, "BPDU received on blocked port %u(%s)\n",
175 (unsigned int) p->port_no, p->dev->name);
176 br_stp_disable_port(p);
177 goto out;
178 }
179
173 buf = skb_pull(skb, 3); 180 buf = skb_pull(skb, 3);
174 181
175 if (buf[0] == BPDU_TYPE_CONFIG) { 182 if (buf[0] == BPDU_TYPE_CONFIG) {
diff --git a/net/bridge/br_sysfs_if.c b/net/bridge/br_sysfs_if.c
index f26173d33d8d..d1dfa4026185 100644
--- a/net/bridge/br_sysfs_if.c
+++ b/net/bridge/br_sysfs_if.c
@@ -156,6 +156,7 @@ static int store_flush(struct net_bridge_port *p, unsigned long v)
156static BRPORT_ATTR(flush, S_IWUSR, NULL, store_flush); 156static BRPORT_ATTR(flush, S_IWUSR, NULL, store_flush);
157 157
158BRPORT_ATTR_FLAG(hairpin_mode, BR_HAIRPIN_MODE); 158BRPORT_ATTR_FLAG(hairpin_mode, BR_HAIRPIN_MODE);
159BRPORT_ATTR_FLAG(bpdu_guard, BR_BPDU_GUARD);
159 160
160#ifdef CONFIG_BRIDGE_IGMP_SNOOPING 161#ifdef CONFIG_BRIDGE_IGMP_SNOOPING
161static ssize_t show_multicast_router(struct net_bridge_port *p, char *buf) 162static ssize_t show_multicast_router(struct net_bridge_port *p, char *buf)
@@ -189,6 +190,7 @@ static const struct brport_attribute *brport_attrs[] = {
189 &brport_attr_hold_timer, 190 &brport_attr_hold_timer,
190 &brport_attr_flush, 191 &brport_attr_flush,
191 &brport_attr_hairpin_mode, 192 &brport_attr_hairpin_mode,
193 &brport_attr_bpdu_guard,
192#ifdef CONFIG_BRIDGE_IGMP_SNOOPING 194#ifdef CONFIG_BRIDGE_IGMP_SNOOPING
193 &brport_attr_multicast_router, 195 &brport_attr_multicast_router,
194#endif 196#endif