aboutsummaryrefslogtreecommitdiffstats
path: root/net/core
diff options
context:
space:
mode:
Diffstat (limited to 'net/core')
-rw-r--r--net/core/dev.c30
-rw-r--r--net/core/dst.c6
-rw-r--r--net/core/net-sysfs.c23
-rw-r--r--net/core/net_namespace.c28
-rw-r--r--net/core/netpoll.c7
5 files changed, 53 insertions, 41 deletions
diff --git a/net/core/dev.c b/net/core/dev.c
index c7e305d13b71..9c58c1ec41a9 100644
--- a/net/core/dev.c
+++ b/net/core/dev.c
@@ -2096,6 +2096,7 @@ int dev_hard_start_xmit(struct sk_buff *skb, struct net_device *dev,
2096{ 2096{
2097 const struct net_device_ops *ops = dev->netdev_ops; 2097 const struct net_device_ops *ops = dev->netdev_ops;
2098 int rc = NETDEV_TX_OK; 2098 int rc = NETDEV_TX_OK;
2099 unsigned int skb_len;
2099 2100
2100 if (likely(!skb->next)) { 2101 if (likely(!skb->next)) {
2101 u32 features; 2102 u32 features;
@@ -2146,8 +2147,9 @@ int dev_hard_start_xmit(struct sk_buff *skb, struct net_device *dev,
2146 } 2147 }
2147 } 2148 }
2148 2149
2150 skb_len = skb->len;
2149 rc = ops->ndo_start_xmit(skb, dev); 2151 rc = ops->ndo_start_xmit(skb, dev);
2150 trace_net_dev_xmit(skb, rc); 2152 trace_net_dev_xmit(skb, rc, dev, skb_len);
2151 if (rc == NETDEV_TX_OK) 2153 if (rc == NETDEV_TX_OK)
2152 txq_trans_update(txq); 2154 txq_trans_update(txq);
2153 return rc; 2155 return rc;
@@ -2167,8 +2169,9 @@ gso:
2167 if (dev->priv_flags & IFF_XMIT_DST_RELEASE) 2169 if (dev->priv_flags & IFF_XMIT_DST_RELEASE)
2168 skb_dst_drop(nskb); 2170 skb_dst_drop(nskb);
2169 2171
2172 skb_len = nskb->len;
2170 rc = ops->ndo_start_xmit(nskb, dev); 2173 rc = ops->ndo_start_xmit(nskb, dev);
2171 trace_net_dev_xmit(nskb, rc); 2174 trace_net_dev_xmit(nskb, rc, dev, skb_len);
2172 if (unlikely(rc != NETDEV_TX_OK)) { 2175 if (unlikely(rc != NETDEV_TX_OK)) {
2173 if (rc & ~NETDEV_TX_MASK) 2176 if (rc & ~NETDEV_TX_MASK)
2174 goto out_kfree_gso_skb; 2177 goto out_kfree_gso_skb;
@@ -3111,7 +3114,7 @@ static int __netif_receive_skb(struct sk_buff *skb)
3111 3114
3112 skb_reset_network_header(skb); 3115 skb_reset_network_header(skb);
3113 skb_reset_transport_header(skb); 3116 skb_reset_transport_header(skb);
3114 skb->mac_len = skb->network_header - skb->mac_header; 3117 skb_reset_mac_len(skb);
3115 3118
3116 pt_prev = NULL; 3119 pt_prev = NULL;
3117 3120
@@ -6175,6 +6178,11 @@ static int dev_cpu_callback(struct notifier_block *nfb,
6175 oldsd->output_queue = NULL; 6178 oldsd->output_queue = NULL;
6176 oldsd->output_queue_tailp = &oldsd->output_queue; 6179 oldsd->output_queue_tailp = &oldsd->output_queue;
6177 } 6180 }
6181 /* Append NAPI poll list from offline CPU. */
6182 if (!list_empty(&oldsd->poll_list)) {
6183 list_splice_init(&oldsd->poll_list, &sd->poll_list);
6184 raise_softirq_irqoff(NET_RX_SOFTIRQ);
6185 }
6178 6186
6179 raise_softirq_irqoff(NET_TX_SOFTIRQ); 6187 raise_softirq_irqoff(NET_TX_SOFTIRQ);
6180 local_irq_enable(); 6188 local_irq_enable();
@@ -6261,29 +6269,23 @@ err_name:
6261/** 6269/**
6262 * netdev_drivername - network driver for the device 6270 * netdev_drivername - network driver for the device
6263 * @dev: network device 6271 * @dev: network device
6264 * @buffer: buffer for resulting name
6265 * @len: size of buffer
6266 * 6272 *
6267 * Determine network driver for device. 6273 * Determine network driver for device.
6268 */ 6274 */
6269char *netdev_drivername(const struct net_device *dev, char *buffer, int len) 6275const char *netdev_drivername(const struct net_device *dev)
6270{ 6276{
6271 const struct device_driver *driver; 6277 const struct device_driver *driver;
6272 const struct device *parent; 6278 const struct device *parent;
6273 6279 const char *empty = "";
6274 if (len <= 0 || !buffer)
6275 return buffer;
6276 buffer[0] = 0;
6277 6280
6278 parent = dev->dev.parent; 6281 parent = dev->dev.parent;
6279
6280 if (!parent) 6282 if (!parent)
6281 return buffer; 6283 return empty;
6282 6284
6283 driver = parent->driver; 6285 driver = parent->driver;
6284 if (driver && driver->name) 6286 if (driver && driver->name)
6285 strlcpy(buffer, driver->name, len); 6287 return driver->name;
6286 return buffer; 6288 return empty;
6287} 6289}
6288 6290
6289static int __netdev_printk(const char *level, const struct net_device *dev, 6291static int __netdev_printk(const char *level, const struct net_device *dev,
diff --git a/net/core/dst.c b/net/core/dst.c
index 9ccca038444f..6135f3671692 100644
--- a/net/core/dst.c
+++ b/net/core/dst.c
@@ -190,7 +190,8 @@ void *dst_alloc(struct dst_ops *ops, struct net_device *dev,
190 dst->lastuse = jiffies; 190 dst->lastuse = jiffies;
191 dst->flags = flags; 191 dst->flags = flags;
192 dst->next = NULL; 192 dst->next = NULL;
193 dst_entries_add(ops, 1); 193 if (!(flags & DST_NOCOUNT))
194 dst_entries_add(ops, 1);
194 return dst; 195 return dst;
195} 196}
196EXPORT_SYMBOL(dst_alloc); 197EXPORT_SYMBOL(dst_alloc);
@@ -243,7 +244,8 @@ again:
243 neigh_release(neigh); 244 neigh_release(neigh);
244 } 245 }
245 246
246 dst_entries_add(dst->ops, -1); 247 if (!(dst->flags & DST_NOCOUNT))
248 dst_entries_add(dst->ops, -1);
247 249
248 if (dst->ops->destroy) 250 if (dst->ops->destroy)
249 dst->ops->destroy(dst); 251 dst->ops->destroy(dst);
diff --git a/net/core/net-sysfs.c b/net/core/net-sysfs.c
index 11b98bc2aa8f..33d2a1fba131 100644
--- a/net/core/net-sysfs.c
+++ b/net/core/net-sysfs.c
@@ -1179,9 +1179,14 @@ static void remove_queue_kobjects(struct net_device *net)
1179#endif 1179#endif
1180} 1180}
1181 1181
1182static const void *net_current_ns(void) 1182static void *net_grab_current_ns(void)
1183{ 1183{
1184 return current->nsproxy->net_ns; 1184 struct net *ns = current->nsproxy->net_ns;
1185#ifdef CONFIG_NET_NS
1186 if (ns)
1187 atomic_inc(&ns->passive);
1188#endif
1189 return ns;
1185} 1190}
1186 1191
1187static const void *net_initial_ns(void) 1192static const void *net_initial_ns(void)
@@ -1196,22 +1201,13 @@ static const void *net_netlink_ns(struct sock *sk)
1196 1201
1197struct kobj_ns_type_operations net_ns_type_operations = { 1202struct kobj_ns_type_operations net_ns_type_operations = {
1198 .type = KOBJ_NS_TYPE_NET, 1203 .type = KOBJ_NS_TYPE_NET,
1199 .current_ns = net_current_ns, 1204 .grab_current_ns = net_grab_current_ns,
1200 .netlink_ns = net_netlink_ns, 1205 .netlink_ns = net_netlink_ns,
1201 .initial_ns = net_initial_ns, 1206 .initial_ns = net_initial_ns,
1207 .drop_ns = net_drop_ns,
1202}; 1208};
1203EXPORT_SYMBOL_GPL(net_ns_type_operations); 1209EXPORT_SYMBOL_GPL(net_ns_type_operations);
1204 1210
1205static void net_kobj_ns_exit(struct net *net)
1206{
1207 kobj_ns_exit(KOBJ_NS_TYPE_NET, net);
1208}
1209
1210static struct pernet_operations kobj_net_ops = {
1211 .exit = net_kobj_ns_exit,
1212};
1213
1214
1215#ifdef CONFIG_HOTPLUG 1211#ifdef CONFIG_HOTPLUG
1216static int netdev_uevent(struct device *d, struct kobj_uevent_env *env) 1212static int netdev_uevent(struct device *d, struct kobj_uevent_env *env)
1217{ 1213{
@@ -1339,6 +1335,5 @@ EXPORT_SYMBOL(netdev_class_remove_file);
1339int netdev_kobject_init(void) 1335int netdev_kobject_init(void)
1340{ 1336{
1341 kobj_ns_type_register(&net_ns_type_operations); 1337 kobj_ns_type_register(&net_ns_type_operations);
1342 register_pernet_subsys(&kobj_net_ops);
1343 return class_register(&net_class); 1338 return class_register(&net_class);
1344} 1339}
diff --git a/net/core/net_namespace.c b/net/core/net_namespace.c
index 6c6b86d0da15..ea489db1bc23 100644
--- a/net/core/net_namespace.c
+++ b/net/core/net_namespace.c
@@ -128,6 +128,7 @@ static __net_init int setup_net(struct net *net)
128 LIST_HEAD(net_exit_list); 128 LIST_HEAD(net_exit_list);
129 129
130 atomic_set(&net->count, 1); 130 atomic_set(&net->count, 1);
131 atomic_set(&net->passive, 1);
131 132
132#ifdef NETNS_REFCNT_DEBUG 133#ifdef NETNS_REFCNT_DEBUG
133 atomic_set(&net->use_count, 0); 134 atomic_set(&net->use_count, 0);
@@ -210,6 +211,13 @@ static void net_free(struct net *net)
210 kmem_cache_free(net_cachep, net); 211 kmem_cache_free(net_cachep, net);
211} 212}
212 213
214void net_drop_ns(void *p)
215{
216 struct net *ns = p;
217 if (ns && atomic_dec_and_test(&ns->passive))
218 net_free(ns);
219}
220
213struct net *copy_net_ns(unsigned long flags, struct net *old_net) 221struct net *copy_net_ns(unsigned long flags, struct net *old_net)
214{ 222{
215 struct net *net; 223 struct net *net;
@@ -230,7 +238,7 @@ struct net *copy_net_ns(unsigned long flags, struct net *old_net)
230 } 238 }
231 mutex_unlock(&net_mutex); 239 mutex_unlock(&net_mutex);
232 if (rv < 0) { 240 if (rv < 0) {
233 net_free(net); 241 net_drop_ns(net);
234 return ERR_PTR(rv); 242 return ERR_PTR(rv);
235 } 243 }
236 return net; 244 return net;
@@ -286,7 +294,7 @@ static void cleanup_net(struct work_struct *work)
286 /* Finally it is safe to free my network namespace structure */ 294 /* Finally it is safe to free my network namespace structure */
287 list_for_each_entry_safe(net, tmp, &net_exit_list, exit_list) { 295 list_for_each_entry_safe(net, tmp, &net_exit_list, exit_list) {
288 list_del_init(&net->exit_list); 296 list_del_init(&net->exit_list);
289 net_free(net); 297 net_drop_ns(net);
290 } 298 }
291} 299}
292static DECLARE_WORK(net_cleanup_work, cleanup_net); 300static DECLARE_WORK(net_cleanup_work, cleanup_net);
@@ -310,19 +318,17 @@ struct net *get_net_ns_by_fd(int fd)
310 struct file *file; 318 struct file *file;
311 struct net *net; 319 struct net *net;
312 320
313 net = ERR_PTR(-EINVAL);
314 file = proc_ns_fget(fd); 321 file = proc_ns_fget(fd);
315 if (!file) 322 if (IS_ERR(file))
316 goto out; 323 return ERR_CAST(file);
317 324
318 ei = PROC_I(file->f_dentry->d_inode); 325 ei = PROC_I(file->f_dentry->d_inode);
319 if (ei->ns_ops != &netns_operations) 326 if (ei->ns_ops == &netns_operations)
320 goto out; 327 net = get_net(ei->ns);
328 else
329 net = ERR_PTR(-EINVAL);
321 330
322 net = get_net(ei->ns); 331 fput(file);
323out:
324 if (file)
325 fput(file);
326 return net; 332 return net;
327} 333}
328 334
diff --git a/net/core/netpoll.c b/net/core/netpoll.c
index 2d7d6d473781..18d9cbda3a39 100644
--- a/net/core/netpoll.c
+++ b/net/core/netpoll.c
@@ -792,6 +792,13 @@ int netpoll_setup(struct netpoll *np)
792 return -ENODEV; 792 return -ENODEV;
793 } 793 }
794 794
795 if (ndev->master) {
796 printk(KERN_ERR "%s: %s is a slave device, aborting.\n",
797 np->name, np->dev_name);
798 err = -EBUSY;
799 goto put;
800 }
801
795 if (!netif_running(ndev)) { 802 if (!netif_running(ndev)) {
796 unsigned long atmost, atleast; 803 unsigned long atmost, atleast;
797 804