static void connect(struct backend_info *be) { int err; struct xenbus_device *dev = be->dev; err = connect_rings(be); if (err) return; err = xen_net_read_mac(dev, be->vif->fe_dev_addr); if (err) { xenbus_dev_fatal(dev, err, "parsing %s/mac", dev->nodename); return; } xen_net_read_rate(dev, &be->vif->credit_bytes, &be->vif->credit_usec); be->vif->remaining_credit = be->vif->credit_bytes; unregister_hotplug_status_watch(be); err = xenbus_watch_pathfmt(dev, &be->hotplug_status_watch, hotplug_status_changed, "%s/%s", dev->nodename, "hotplug-status"); if (err) { /* Switch now, since we can't do a watch. */ xenbus_switch_state(dev, XenbusStateConnected); } else { be->have_hotplug_status_watch = 1; } netif_wake_queue(be->vif->dev); }
static void connect(struct backend_info *be) { int err; struct xenbus_device *dev = be->dev; rtnl_lock(); err = xen_net_read_mac(dev, be->netif->fe_dev_addr); if (err) { xenbus_dev_fatal(dev, err, "parsing %s/mac", dev->nodename); goto out; } xen_net_read_rate(dev, &be->netif->credit_bytes, &be->netif->credit_usec); be->netif->remaining_credit = be->netif->credit_bytes; err = connect_rings(be); if (err) goto out; /* May not get a kick from the frontend, so start the tx_queue now. */ if (!netbk_can_queue(be->netif->dev)) netif_wake_queue(be->netif->dev); out: rtnl_unlock(); }
static void connect(struct backend_info *be) { int err; struct xenbus_device *dev = be->dev; err = connect_rings(be); if (err) return; err = xen_net_read_mac(dev, be->vif->fe_dev_addr); if (err) { xenbus_dev_fatal(dev, err, "parsing %s/mac", dev->nodename); return; } /* mlr-begin : read the priority the vif*/ /* err = xen_read_priority(dev, &(be->vif->priority)); if (err) { xenbus_dev_fatal(dev, err, "parsing %s/priority", dev->nodename); return; } */ /* mlr-end */ /* mlr-begin : changed, add para '&be->vif->credit_initial' */ xen_net_read_rate(dev, &be->vif->credit_bytes, &be->vif->credit_usec, &be->vif->credit_initial); printk("mlr: vif-%s credit initial is %ld\n", be->vif->dev->name, be->vif->credit_initial); /* mlr-end */ be->vif->remaining_credit = be->vif->credit_bytes; unregister_hotplug_status_watch(be); err = xenbus_watch_pathfmt(dev, &be->hotplug_status_watch, hotplug_status_changed, "%s/%s", dev->nodename, "hotplug-status"); if (err) { /* Switch now, since we can't do a watch. */ xenbus_switch_state(dev, XenbusStateConnected); } else { be->have_hotplug_status_watch = 1; } netif_wake_queue(be->vif->dev); }
static void xen_net_rate_changed(struct xenbus_watch *watch, const char **vec, unsigned int len) { struct xenvif *vif = container_of(watch, struct xenvif, credit_watch); struct xenbus_device *dev = xenvif_to_xenbus_device(vif); unsigned long credit_bytes; unsigned long credit_usec; unsigned int queue_index; xen_net_read_rate(dev, &credit_bytes, &credit_usec); for (queue_index = 0; queue_index < vif->num_queues; queue_index++) { struct xenvif_queue *queue = &vif->queues[queue_index]; queue->credit_bytes = credit_bytes; queue->credit_usec = credit_usec; if (!mod_timer_pending(&queue->credit_timeout, jiffies) && queue->remaining_credit > queue->credit_bytes) { queue->remaining_credit = queue->credit_bytes; } } }
static void connect(struct backend_info *be) { int err; struct xenbus_device *dev = be->dev; err = connect_rings(be); if (err) return; err = xen_net_read_mac(dev, be->netif->fe_dev_addr); if (err) { xenbus_dev_fatal(dev, err, "parsing %s/mac", dev->nodename); return; } xen_net_read_rate(dev, &be->netif->credit_bytes, &be->netif->credit_usec); be->netif->remaining_credit = be->netif->credit_bytes; xenbus_switch_state(dev, XenbusStateConnected); }
static void connect(struct backend_info *be) { int err; struct xenbus_device *dev = be->dev; unsigned long credit_bytes, credit_usec; unsigned int queue_index; unsigned int requested_num_queues; struct xenvif_queue *queue; /* Check whether the frontend requested multiple queues * and read the number requested. */ err = xenbus_scanf(XBT_NIL, dev->otherend, "multi-queue-num-queues", "%u", &requested_num_queues); if (err < 0) { requested_num_queues = 1; /* Fall back to single queue */ } else if (requested_num_queues > xenvif_max_queues) { /* buggy or malicious guest */ xenbus_dev_fatal(dev, err, "guest requested %u queues, exceeding the maximum of %u.", requested_num_queues, xenvif_max_queues); return; } err = xen_net_read_mac(dev, be->vif->fe_dev_addr); if (err) { xenbus_dev_fatal(dev, err, "parsing %s/mac", dev->nodename); return; } xen_net_read_rate(dev, &credit_bytes, &credit_usec); xen_unregister_watchers(be->vif); xen_register_watchers(dev, be->vif); read_xenbus_vif_flags(be); err = connect_ctrl_ring(be); if (err) { xenbus_dev_fatal(dev, err, "connecting control ring"); return; } /* Use the number of queues requested by the frontend */ be->vif->queues = vzalloc(requested_num_queues * sizeof(struct xenvif_queue)); if (!be->vif->queues) { xenbus_dev_fatal(dev, -ENOMEM, "allocating queues"); return; } be->vif->num_queues = requested_num_queues; be->vif->stalled_queues = requested_num_queues; for (queue_index = 0; queue_index < requested_num_queues; ++queue_index) { queue = &be->vif->queues[queue_index]; queue->vif = be->vif; queue->id = queue_index; snprintf(queue->name, sizeof(queue->name), "%s-q%u", be->vif->dev->name, queue->id); err = xenvif_init_queue(queue); if (err) { /* xenvif_init_queue() cleans up after itself on * failure, but we need to clean up any previously * initialised queues. Set num_queues to i so that * earlier queues can be destroyed using the regular * disconnect logic. */ be->vif->num_queues = queue_index; goto err; } queue->credit_bytes = credit_bytes; queue->remaining_credit = credit_bytes; queue->credit_usec = credit_usec; err = connect_data_rings(be, queue); if (err) { /* connect_data_rings() cleans up after itself on * failure, but we need to clean up after * xenvif_init_queue() here, and also clean up any * previously initialised queues. */ xenvif_deinit_queue(queue); be->vif->num_queues = queue_index; goto err; } } #ifdef CONFIG_DEBUG_FS xenvif_debugfs_addif(be->vif); #endif /* CONFIG_DEBUG_FS */ /* Initialisation completed, tell core driver the number of * active queues. */ rtnl_lock(); netif_set_real_num_tx_queues(be->vif->dev, requested_num_queues); netif_set_real_num_rx_queues(be->vif->dev, requested_num_queues); rtnl_unlock(); xenvif_carrier_on(be->vif); unregister_hotplug_status_watch(be); err = xenbus_watch_pathfmt(dev, &be->hotplug_status_watch, hotplug_status_changed, "%s/%s", dev->nodename, "hotplug-status"); if (!err) be->have_hotplug_status_watch = 1; netif_tx_wake_all_queues(be->vif->dev); return; err: if (be->vif->num_queues > 0) xenvif_disconnect_data(be->vif); /* Clean up existing queues */ vfree(be->vif->queues); be->vif->queues = NULL; be->vif->num_queues = 0; xenvif_disconnect_ctrl(be->vif); return; }