patch-2_6_7-vs1_9_1_12
[linux-2.6.git] / net / bridge / br_if.c
1 /*
2  *      Userspace interface
3  *      Linux ethernet bridge
4  *
5  *      Authors:
6  *      Lennert Buytenhek               <buytenh@gnu.org>
7  *
8  *      $Id: br_if.c,v 1.7 2001/12/24 00:59:55 davem Exp $
9  *
10  *      This program is free software; you can redistribute it and/or
11  *      modify it under the terms of the GNU General Public License
12  *      as published by the Free Software Foundation; either version
13  *      2 of the License, or (at your option) any later version.
14  */
15
16 #include <linux/kernel.h>
17 #include <linux/netdevice.h>
18 #include <linux/ethtool.h>
19 #include <linux/if_arp.h>
20 #include <linux/module.h>
21 #include <linux/init.h>
22 #include <linux/rtnetlink.h>
23 #include <net/sock.h>
24
25 #include "br_private.h"
26
27 /*
28  * Determine initial path cost based on speed.
29  * using recommendations from 802.1d standard
30  *
31  * Need to simulate user ioctl because not all device's that support
32  * ethtool, use ethtool_ops.  Also, since driver might sleep need to
33  * not be holding any locks.
34  */
35 static int br_initial_port_cost(struct net_device *dev)
36 {
37
38         struct ethtool_cmd ecmd = { ETHTOOL_GSET };
39         struct ifreq ifr;
40         mm_segment_t old_fs;
41         int err;
42
43         strncpy(ifr.ifr_name, dev->name, IFNAMSIZ);
44         ifr.ifr_data = (void *) &ecmd;
45
46         old_fs = get_fs();
47         set_fs(KERNEL_DS);
48         err = dev_ethtool(&ifr);
49         set_fs(old_fs);
50         
51         if (!err) {
52                 switch(ecmd.speed) {
53                 case SPEED_100:
54                         return 19;
55                 case SPEED_1000:
56                         return 4;
57                 case SPEED_10000:
58                         return 2;
59                 case SPEED_10:
60                         return 100;
61                 default:
62                         pr_info("bridge: can't decode speed from %s: %d\n",
63                                 dev->name, ecmd.speed);
64                         return 100;
65                 }
66         }
67
68         /* Old silly heuristics based on name */
69         if (!strncmp(dev->name, "lec", 3))
70                 return 7;
71
72         if (!strncmp(dev->name, "plip", 4))
73                 return 2500;
74
75         return 100;     /* assume old 10Mbps */
76 }
77
78 static void destroy_nbp(void *arg)
79 {
80         struct net_bridge_port *p = arg;
81         struct net_device *dev = p->dev;
82
83         dev->br_port = NULL;
84         p->br = NULL;
85         p->dev = NULL;
86         dev_put(dev);
87
88         br_sysfs_freeif(p);
89 }
90
91 /* called with RTNL */
92 static void del_nbp(struct net_bridge_port *p)
93 {
94         struct net_bridge *br = p->br;
95         struct net_device *dev = p->dev;
96
97         dev_set_promiscuity(dev, -1);
98
99         spin_lock_bh(&br->lock);
100         br_stp_disable_port(p);
101         spin_unlock_bh(&br->lock);
102
103         br_fdb_delete_by_port(br, p);
104
105         list_del_rcu(&p->list);
106
107         del_timer_sync(&p->message_age_timer);
108         del_timer_sync(&p->forward_delay_timer);
109         del_timer_sync(&p->hold_timer);
110         
111         call_rcu(&p->rcu, destroy_nbp, p);
112 }
113
114 /* called with RTNL */
115 static void del_br(struct net_bridge *br)
116 {
117         struct net_bridge_port *p, *n;
118
119         list_for_each_entry_safe(p, n, &br->port_list, list) {
120                 br_sysfs_removeif(p);
121                 del_nbp(p);
122         }
123
124         del_timer_sync(&br->gc_timer);
125
126         br_sysfs_delbr(br->dev);
127         unregister_netdevice(br->dev);
128 }
129
130 static struct net_device *new_bridge_dev(const char *name)
131 {
132         struct net_bridge *br;
133         struct net_device *dev;
134
135         dev = alloc_netdev(sizeof(struct net_bridge), name,
136                            br_dev_setup);
137         
138         if (!dev)
139                 return NULL;
140
141         br = netdev_priv(dev);
142         br->dev = dev;
143
144         br->lock = SPIN_LOCK_UNLOCKED;
145         INIT_LIST_HEAD(&br->port_list);
146         br->hash_lock = RW_LOCK_UNLOCKED;
147
148         br->bridge_id.prio[0] = 0x80;
149         br->bridge_id.prio[1] = 0x00;
150         memset(br->bridge_id.addr, 0, ETH_ALEN);
151
152         br->stp_enabled = 0;
153         br->designated_root = br->bridge_id;
154         br->root_path_cost = 0;
155         br->root_port = 0;
156         br->bridge_max_age = br->max_age = 20 * HZ;
157         br->bridge_hello_time = br->hello_time = 2 * HZ;
158         br->bridge_forward_delay = br->forward_delay = 15 * HZ;
159         br->topology_change = 0;
160         br->topology_change_detected = 0;
161         br->ageing_time = 300 * HZ;
162         INIT_LIST_HEAD(&br->age_list);
163
164         br_stp_timer_init(br);
165
166         return dev;
167 }
168
169 /* find an available port number */
170 static int find_portno(struct net_bridge *br)
171 {
172         int index;
173         struct net_bridge_port *p;
174         unsigned long *inuse;
175
176         inuse = kmalloc(BITS_TO_LONGS(BR_MAX_PORTS)*sizeof(unsigned long),
177                         GFP_KERNEL);
178         if (!inuse)
179                 return -ENOMEM;
180
181         memset(inuse, 0, BITS_TO_LONGS(BR_MAX_PORTS)*sizeof(unsigned long));
182         set_bit(0, inuse);      /* zero is reserved */
183         list_for_each_entry(p, &br->port_list, list) {
184                 set_bit(p->port_no, inuse);
185         }
186         index = find_first_zero_bit(inuse, BR_MAX_PORTS);
187         kfree(inuse);
188
189         return (index >= BR_MAX_PORTS) ? -EXFULL : index;
190 }
191
192 /* called with RTNL */
193 static struct net_bridge_port *new_nbp(struct net_bridge *br, 
194                                        struct net_device *dev,
195                                        unsigned long cost)
196 {
197         int index;
198         struct net_bridge_port *p;
199         
200         index = find_portno(br);
201         if (index < 0)
202                 return ERR_PTR(index);
203
204         p = kmalloc(sizeof(*p), GFP_KERNEL);
205         if (p == NULL)
206                 return ERR_PTR(-ENOMEM);
207
208         memset(p, 0, sizeof(*p));
209         p->br = br;
210         dev_hold(dev);
211         p->dev = dev;
212         p->path_cost = cost;
213         p->priority = 0x8000 >> BR_PORT_BITS;
214         dev->br_port = p;
215         p->port_no = index;
216         br_init_port(p);
217         p->state = BR_STATE_DISABLED;
218         kobject_init(&p->kobj);
219
220         return p;
221 }
222
223 int br_add_bridge(const char *name)
224 {
225         struct net_device *dev;
226         int ret;
227
228         dev = new_bridge_dev(name);
229         if (!dev) 
230                 return -ENOMEM;
231
232         rtnl_lock();
233         if (strchr(dev->name, '%')) {
234                 ret = dev_alloc_name(dev, dev->name);
235                 if (ret < 0)
236                         goto err1;
237         }
238
239         ret = register_netdevice(dev);
240         if (ret)
241                 goto err2;
242
243         /* network device kobject is not setup until
244          * after rtnl_unlock does it's hotplug magic.
245          * so hold reference to avoid race.
246          */
247         dev_hold(dev);
248         rtnl_unlock();
249
250         ret = br_sysfs_addbr(dev);
251         dev_put(dev);
252
253         if (ret) 
254                 unregister_netdev(dev);
255  out:
256         return ret;
257
258  err2:
259         free_netdev(dev);
260  err1:
261         rtnl_unlock();
262         goto out;
263 }
264
265 int br_del_bridge(const char *name)
266 {
267         struct net_device *dev;
268         int ret = 0;
269
270         rtnl_lock();
271         dev = __dev_get_by_name(name);
272         if (dev == NULL) 
273                 ret =  -ENXIO;  /* Could not find device */
274
275         else if (!(dev->priv_flags & IFF_EBRIDGE)) {
276                 /* Attempt to delete non bridge device! */
277                 ret = -EPERM;
278         }
279
280         else if (dev->flags & IFF_UP) {
281                 /* Not shutdown yet. */
282                 ret = -EBUSY;
283         } 
284
285         else 
286                 del_br(netdev_priv(dev));
287
288         rtnl_unlock();
289         return ret;
290 }
291
292 /* called with RTNL */
293 int br_add_if(struct net_bridge *br, struct net_device *dev)
294 {
295         struct net_bridge_port *p;
296         int err = 0;
297
298         if (dev->flags & IFF_LOOPBACK || dev->type != ARPHRD_ETHER)
299                 return -EINVAL;
300
301         if (dev->hard_start_xmit == br_dev_xmit)
302                 return -ELOOP;
303
304         if (dev->br_port != NULL)
305                 return -EBUSY;
306
307         if (IS_ERR(p = new_nbp(br, dev, br_initial_port_cost(dev))))
308                 return PTR_ERR(p);
309
310         if ((err = br_fdb_insert(br, p, dev->dev_addr, 1)))
311                 destroy_nbp(p);
312  
313         else if ((err = br_sysfs_addif(p)))
314                 del_nbp(p);
315         else {
316                 dev_set_promiscuity(dev, 1);
317
318                 list_add_rcu(&p->list, &br->port_list);
319
320                 spin_lock_bh(&br->lock);
321                 br_stp_recalculate_bridge_id(br);
322                 if ((br->dev->flags & IFF_UP) && (dev->flags & IFF_UP))
323                         br_stp_enable_port(p);
324                 spin_unlock_bh(&br->lock);
325         }
326
327         return err;
328 }
329
330 /* called with RTNL */
331 int br_del_if(struct net_bridge *br, struct net_device *dev)
332 {
333         struct net_bridge_port *p = dev->br_port;
334         
335         if (!p || p->br != br) 
336                 return -EINVAL;
337
338         br_sysfs_removeif(p);
339         del_nbp(p);
340
341         spin_lock_bh(&br->lock);
342         br_stp_recalculate_bridge_id(br);
343         spin_unlock_bh(&br->lock);
344
345         return 0;
346 }
347
348 void __exit br_cleanup_bridges(void)
349 {
350         struct net_device *dev, *nxt;
351
352         rtnl_lock();
353         for (dev = dev_base; dev; dev = nxt) {
354                 nxt = dev->next;
355                 if (dev->priv_flags & IFF_EBRIDGE)
356                         del_br(dev->priv);
357         }
358         rtnl_unlock();
359
360 }