Update to 3.4-final.
[linux-flexiantxendom0-3.2.10.git] / drivers / xen / netback / xenbus.c
1 /*  Xenbus code for netif backend
2     Copyright (C) 2005 Rusty Russell <rusty@rustcorp.com.au>
3     Copyright (C) 2005 XenSource Ltd
4
5     This program is free software; you can redistribute it and/or modify
6     it under the terms of the GNU General Public License as published by
7     the Free Software Foundation; either version 2 of the License, or
8     (at your option) any later version.
9
10     This program is distributed in the hope that it will be useful,
11     but WITHOUT ANY WARRANTY; without even the implied warranty of
12     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13     GNU General Public License for more details.
14
15     You should have received a copy of the GNU General Public License
16     along with this program; if not, write to the Free Software
17     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
18 */
19
20 #include <stdarg.h>
21 #include <linux/rwsem.h>
22 #include <xen/xenbus.h>
23 #include "common.h"
24
25 #if 0
26 #undef DPRINTK
27 #define DPRINTK(fmt, args...) \
28     printk("netback/xenbus (%s:%d) " fmt ".\n", __FUNCTION__, __LINE__, ##args)
29 #endif
30
31 static DECLARE_RWSEM(teardown_sem);
32
33 static int connect_rings(struct backend_info *);
34 static void connect(struct backend_info *);
35 static void backend_create_netif(struct backend_info *be);
36 static void unregister_hotplug_status_watch(struct backend_info *be);
37 static void netback_disconnect(struct device *, bool);
38
39 static int netback_remove(struct xenbus_device *dev)
40 {
41         struct backend_info *be = dev_get_drvdata(&dev->dev);
42
43         netback_remove_accelerators(be, dev);
44
45         netback_disconnect(&dev->dev, true);
46         kfree(be);
47         return 0;
48 }
49
50 static void netback_disconnect(struct device *xbdev_dev, bool clear)
51 {
52         struct backend_info *be = dev_get_drvdata(xbdev_dev);
53
54         unregister_hotplug_status_watch(be);
55         if (be->netif)
56                 kobject_uevent(&xbdev_dev->kobj, KOBJ_OFFLINE);
57
58         xenbus_rm(XBT_NIL, be->dev->nodename, "hotplug-status");
59
60         down_write(&teardown_sem);
61         if (be->netif) {
62                 netif_disconnect(be);
63                 be->netif = NULL;
64         }
65         if (clear)
66                 dev_set_drvdata(xbdev_dev, NULL);
67         up_write(&teardown_sem);
68 }
69
70 /**
71  * Entry point to this code when a new device is created.  Allocate the basic
72  * structures and switch to InitWait.
73  */
74 static int netback_probe(struct xenbus_device *dev,
75                          const struct xenbus_device_id *id)
76 {
77         const char *message;
78         struct xenbus_transaction xbt;
79         int err;
80         int sg;
81         struct backend_info *be = kzalloc(sizeof(struct backend_info),
82                                           GFP_KERNEL);
83         if (!be) {
84                 xenbus_dev_fatal(dev, -ENOMEM,
85                                  "allocating backend structure");
86                 return -ENOMEM;
87         }
88
89         be->dev = dev;
90         dev_set_drvdata(&dev->dev, be);
91
92         sg = 1;
93         if (netbk_copy_skb_mode == NETBK_ALWAYS_COPY_SKB)
94                 sg = 0;
95
96         do {
97                 err = xenbus_transaction_start(&xbt);
98                 if (err) {
99                         xenbus_dev_fatal(dev, err, "starting transaction");
100                         goto fail;
101                 }
102
103                 err = xenbus_printf(xbt, dev->nodename, "feature-sg", "%d", sg);
104                 if (err) {
105                         message = "writing feature-sg";
106                         goto abort_transaction;
107                 }
108
109                 err = xenbus_printf(xbt, dev->nodename, "feature-gso-tcpv4",
110                                     "%d", sg);
111                 if (err) {
112                         message = "writing feature-gso-tcpv4";
113                         goto abort_transaction;
114                 }
115
116                 /* We support rx-copy path. */
117                 err = xenbus_printf(xbt, dev->nodename,
118                                     "feature-rx-copy", "%d", 1);
119                 if (err) {
120                         message = "writing feature-rx-copy";
121                         goto abort_transaction;
122                 }
123
124                 /*
125                  * We don't support rx-flip path (except old guests who don't
126                  * grok this feature flag).
127                  */
128                 err = xenbus_printf(xbt, dev->nodename,
129                                     "feature-rx-flip", "%d", 0);
130                 if (err) {
131                         message = "writing feature-rx-flip";
132                         goto abort_transaction;
133                 }
134
135                 err = xenbus_transaction_end(xbt, 0);
136         } while (err == -EAGAIN);
137
138         if (err) {
139                 xenbus_dev_fatal(dev, err, "completing transaction");
140                 goto fail;
141         }
142
143         netback_probe_accelerators(be, dev);
144
145         err = xenbus_switch_state(dev, XenbusStateInitWait);
146         if (err)
147                 goto fail;
148
149         /* This kicks hotplug scripts, so do it immediately. */
150         backend_create_netif(be);
151
152         return 0;
153
154 abort_transaction:
155         xenbus_transaction_end(xbt, 1);
156         xenbus_dev_fatal(dev, err, "%s", message);
157 fail:
158         DPRINTK("failed");
159         netback_remove(dev);
160         return err;
161 }
162
163
164 /**
165  * Handle the creation of the hotplug script environment.  We add the script
166  * and vif variables to the environment, for the benefit of the vif-* hotplug
167  * scripts.
168  */
169 static int netback_uevent(struct xenbus_device *xdev, struct kobj_uevent_env *env)
170 {
171         struct backend_info *be;
172         char *val;
173
174         DPRINTK("netback_uevent");
175
176         val = xenbus_read(XBT_NIL, xdev->nodename, "script", NULL);
177         if (IS_ERR(val)) {
178                 int err = PTR_ERR(val);
179                 xenbus_dev_fatal(xdev, err, "reading script");
180                 return err;
181         }
182
183         add_uevent_var(env, "script=%s", val);
184         kfree(val);
185
186         down_read(&teardown_sem);
187         be = dev_get_drvdata(&xdev->dev);
188         if (be && be->netif)
189                 add_uevent_var(env, "vif=%s", be->netif->dev->name);
190         up_read(&teardown_sem);
191
192         return 0;
193 }
194
195
196 static void backend_create_netif(struct backend_info *be)
197 {
198         int err;
199         long handle;
200         struct xenbus_device *dev = be->dev;
201         netif_t *netif;
202
203         if (be->netif != NULL)
204                 return;
205
206         err = xenbus_scanf(XBT_NIL, dev->nodename, "handle", "%li", &handle);
207         if (err != 1) {
208                 xenbus_dev_fatal(dev, err, "reading handle");
209                 return;
210         }
211
212         netif = netif_alloc(&dev->dev, dev->otherend_id, handle);
213         if (IS_ERR(netif)) {
214                 err = PTR_ERR(netif);
215                 xenbus_dev_fatal(dev, err, "creating interface");
216                 return;
217         }
218         be->netif = netif;
219
220         kobject_uevent(&dev->dev.kobj, KOBJ_ONLINE);
221 }
222
223
224 /**
225  * Callback received when the frontend's state changes.
226  */
227 static void frontend_changed(struct xenbus_device *dev,
228                              enum xenbus_state frontend_state)
229 {
230         struct backend_info *be = dev_get_drvdata(&dev->dev);
231
232         DPRINTK("%s", xenbus_strstate(frontend_state));
233
234         be->frontend_state = frontend_state;
235
236         switch (frontend_state) {
237         case XenbusStateInitialising:
238                 if (dev->state == XenbusStateClosed) {
239                         pr_info("%s: %s: prepare for reconnect\n",
240                                 __FUNCTION__, dev->nodename);
241                         xenbus_switch_state(dev, XenbusStateInitWait);
242                 }
243                 break;
244
245         case XenbusStateInitialised:
246                 break;
247
248         case XenbusStateConnected:
249                 if (dev->state == XenbusStateConnected)
250                         break;
251
252                 /* backend_create_netif() is idempotent */
253                 backend_create_netif(be);
254                 if (be->netif)
255                         connect(be);
256                 break;
257
258         case XenbusStateClosing:
259                 netback_disconnect(&dev->dev, false);
260                 xenbus_switch_state(dev, XenbusStateClosing);
261                 break;
262
263         case XenbusStateClosed:
264                 xenbus_switch_state(dev, XenbusStateClosed);
265                 if (xenbus_dev_is_online(dev))
266                         break;
267                 /* fall through if not online */
268         case XenbusStateUnknown:
269                 /* implies netback_disconnect() via netback_remove() */
270                 device_unregister(&dev->dev);
271                 break;
272
273         default:
274                 xenbus_dev_fatal(dev, -EINVAL, "saw state %d at frontend",
275                                  frontend_state);
276                 break;
277         }
278 }
279
280
281 static void xen_net_read_rate(struct xenbus_device *dev,
282                               unsigned long *bytes, unsigned long *usec)
283 {
284         char *s, *e;
285         unsigned long b, u;
286         char *ratestr;
287
288         /* Default to unlimited bandwidth. */
289         *bytes = ~0UL;
290         *usec = 0;
291
292         ratestr = xenbus_read(XBT_NIL, dev->nodename, "rate", NULL);
293         if (IS_ERR(ratestr))
294                 return;
295
296         s = ratestr;
297         b = simple_strtoul(s, &e, 10);
298         if ((s == e) || (*e != ','))
299                 goto fail;
300
301         s = e + 1;
302         u = simple_strtoul(s, &e, 10);
303         if ((s == e) || (*e != '\0'))
304                 goto fail;
305
306         *bytes = b;
307         *usec = u;
308
309         kfree(ratestr);
310         return;
311
312  fail:
313         WPRINTK("Failed to parse network rate limit. Traffic unlimited.\n");
314         kfree(ratestr);
315 }
316
317 static int xen_net_read_mac(struct xenbus_device *dev, u8 mac[])
318 {
319         char *s, *e, *macstr;
320         int i;
321
322         macstr = s = xenbus_read(XBT_NIL, dev->nodename, "mac", NULL);
323         if (IS_ERR(macstr))
324                 return PTR_ERR(macstr);
325
326         for (i = 0; i < ETH_ALEN; i++) {
327                 mac[i] = simple_strtoul(s, &e, 16);
328                 if ((s == e) || (*e != ((i == ETH_ALEN-1) ? '\0' : ':'))) {
329                         kfree(macstr);
330                         return -ENOENT;
331                 }
332                 s = e+1;
333         }
334
335         kfree(macstr);
336         return 0;
337 }
338
339 static void unregister_hotplug_status_watch(struct backend_info *be)
340 {
341         if (be->have_hotplug_status_watch) {
342                 unregister_xenbus_watch(&be->hotplug_status_watch);
343                 kfree(be->hotplug_status_watch.node);
344         }
345         be->have_hotplug_status_watch = 0;
346 }
347
348 static void hotplug_status_changed(struct xenbus_watch *watch,
349                                    const char **vec,
350                                    unsigned int vec_size)
351 {
352         struct backend_info *be = container_of(watch,
353                                                struct backend_info,
354                                                hotplug_status_watch);
355         char *str;
356         unsigned int len;
357
358         str = xenbus_read(XBT_NIL, be->dev->nodename, "hotplug-status", &len);
359         if (IS_ERR(str))
360                 return;
361         if (len == sizeof("connected")-1 && !memcmp(str, "connected", len)) {
362                 xenbus_switch_state(be->dev, XenbusStateConnected);
363                 /* Not interested in this watch anymore. */
364                 unregister_hotplug_status_watch(be);
365         }
366         kfree(str);
367 }
368
369 static void connect(struct backend_info *be)
370 {
371         int err;
372         struct xenbus_device *dev = be->dev;
373
374         err = connect_rings(be);
375         if (err)
376                 return;
377
378         err = xen_net_read_mac(dev, be->netif->fe_dev_addr);
379         if (err) {
380                 xenbus_dev_fatal(dev, err, "parsing %s/mac", dev->nodename);
381                 return;
382         }
383
384         xen_net_read_rate(dev, &be->netif->credit_bytes,
385                           &be->netif->credit_usec);
386         be->netif->remaining_credit = be->netif->credit_bytes;
387
388         unregister_hotplug_status_watch(be);
389         err = xenbus_watch_path2(dev, dev->nodename, "hotplug-status",
390                                  &be->hotplug_status_watch,
391                                  hotplug_status_changed);
392         if (err) {
393                 /* Switch now, since we can't do a watch. */
394                 xenbus_switch_state(dev, XenbusStateConnected);
395         } else {
396                 be->have_hotplug_status_watch = 1;
397         }
398
399         netif_wake_queue(be->netif->dev);
400 }
401
402
403 static int connect_rings(struct backend_info *be)
404 {
405         netif_t *netif = be->netif;
406         struct xenbus_device *dev = be->dev;
407         unsigned int tx_ring_ref, rx_ring_ref;
408         unsigned int evtchn, rx_copy;
409         int err;
410         int val;
411
412         DPRINTK("");
413
414         err = xenbus_gather(XBT_NIL, dev->otherend,
415                             "tx-ring-ref", "%u", &tx_ring_ref,
416                             "rx-ring-ref", "%u", &rx_ring_ref,
417                             "event-channel", "%u", &evtchn, NULL);
418         if (err) {
419                 xenbus_dev_fatal(dev, err,
420                                  "reading %s/ring-ref and event-channel",
421                                  dev->otherend);
422                 return err;
423         }
424
425         err = xenbus_scanf(XBT_NIL, dev->otherend, "request-rx-copy", "%u",
426                            &rx_copy);
427         if (err == -ENOENT) {
428                 err = 0;
429                 rx_copy = 0;
430         }
431         if (err < 0) {
432                 xenbus_dev_fatal(dev, err, "reading %s/request-rx-copy",
433                                  dev->otherend);
434                 return err;
435         }
436         netif->copying_receiver = !!rx_copy;
437
438         if (netif->dev->tx_queue_len != 0) {
439                 if (xenbus_scanf(XBT_NIL, dev->otherend,
440                                  "feature-rx-notify", "%d", &val) < 0)
441                         val = 0;
442                 if (val)
443                         netif->can_queue = 1;
444                 else
445                         /* Must be non-zero for pfifo_fast to work. */
446                         netif->dev->tx_queue_len = 1;
447         }
448
449         if (xenbus_scanf(XBT_NIL, dev->otherend, "feature-sg", "%d", &val) < 0)
450                 val = 0;
451         netif->can_sg = !!val;
452
453         if (xenbus_scanf(XBT_NIL, dev->otherend, "feature-gso-tcpv4", "%d",
454                          &val) < 0)
455                 val = 0;
456         netif->gso = !!val;
457
458         if (xenbus_scanf(XBT_NIL, dev->otherend, "feature-no-csum-offload",
459                          "%d", &val) < 0)
460                 val = 0;
461         netif->csum = !val;
462
463         /* Map the shared frame, irq etc. */
464         err = netif_map(be, tx_ring_ref, rx_ring_ref, evtchn);
465         if (err) {
466                 xenbus_dev_fatal(dev, err,
467                                  "mapping shared-frames %u/%u port %u",
468                                  tx_ring_ref, rx_ring_ref, evtchn);
469                 return err;
470         }
471         return 0;
472 }
473
474
475 /* ** Driver Registration ** */
476
477
478 static const struct xenbus_device_id netback_ids[] = {
479         { "vif" },
480         { "" }
481 };
482
483 static DEFINE_XENBUS_DRIVER(netback, ,
484         .probe = netback_probe,
485         .remove = netback_remove,
486         .uevent = netback_uevent,
487         .otherend_changed = frontend_changed,
488 );
489
490
491 void netif_xenbus_init(void)
492 {
493         WARN_ON(xenbus_register_backend(&netback_driver));
494 }