diff options
author | Jeff Dike <jdike@addtoit.com> | 2007-10-16 04:27:31 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@woody.linux-foundation.org> | 2007-10-16 12:43:08 -0400 |
commit | b53f35a8093e6aed7e8e880eaa0b89a3d2fdfb0a (patch) | |
tree | 50e19688753650e27b1f7fc1d48eb8683666e6b7 /arch/um | |
parent | cd1ae0e49bdd814cfaa2e5ab28cff21a30e20085 (diff) |
uml: network driver MTU cleanups
A bunch of MTU-related cleanups in the network code.
First, there is the addition of the notion of a maximally-sized packet, which
is the MTU plus headers. This is used to size the skb that will receive a
packet. This allows ether_adjust_skb to go away, as it was used to resize the
skb after it was allocated.
Since the skb passed into the low-level read routine is no longer resized, and
possibly reallocated, there, they (and the write routines) don't need to get
an sk_buff **. They just need the sk_buff * now. The callers of
ether_adjust_skb still need to do the skb_put, so that's now inlined.
The MAX_PACKET definitions in most of the drivers are gone.
The set_mtu methods were all the same and did nothing, so they can be
removed.
The ethertap driver had a typo which doubled the size of the packet rather
than adding two bytes to it. It also wasn't defining its setup_size, causing
a zero-byte kmalloc and crash when the invalid pointer returned from kmalloc
was dereferenced.
Signed-off-by: Jeff Dike <jdike@linux.intel.com>
Signed-off-by: Andrew Morton <akpm@linux-foundation.org>
Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'arch/um')
-rw-r--r-- | arch/um/drivers/daemon_kern.c | 15 | ||||
-rw-r--r-- | arch/um/drivers/daemon_user.c | 11 | ||||
-rw-r--r-- | arch/um/drivers/mcast_kern.c | 13 | ||||
-rw-r--r-- | arch/um/drivers/mcast_user.c | 11 | ||||
-rw-r--r-- | arch/um/drivers/net_kern.c | 42 | ||||
-rw-r--r-- | arch/um/drivers/pcap_kern.c | 13 | ||||
-rw-r--r-- | arch/um/drivers/pcap_user.c | 9 | ||||
-rw-r--r-- | arch/um/drivers/slip_kern.c | 10 | ||||
-rw-r--r-- | arch/um/drivers/slip_user.c | 9 | ||||
-rw-r--r-- | arch/um/drivers/slirp_kern.c | 14 | ||||
-rw-r--r-- | arch/um/drivers/slirp_user.c | 9 | ||||
-rw-r--r-- | arch/um/drivers/vde_kern.c | 19 | ||||
-rw-r--r-- | arch/um/drivers/vde_user.c | 11 | ||||
-rw-r--r-- | arch/um/include/net_kern.h | 13 | ||||
-rw-r--r-- | arch/um/include/net_user.h | 4 | ||||
-rw-r--r-- | arch/um/os-Linux/drivers/ethertap_kern.c | 30 | ||||
-rw-r--r-- | arch/um/os-Linux/drivers/ethertap_user.c | 9 | ||||
-rw-r--r-- | arch/um/os-Linux/drivers/tuntap_kern.c | 15 | ||||
-rw-r--r-- | arch/um/os-Linux/drivers/tuntap_user.c | 11 |
19 files changed, 80 insertions, 188 deletions
diff --git a/arch/um/drivers/daemon_kern.c b/arch/um/drivers/daemon_kern.c index ac507bb87fea..d53ff52bb404 100644 --- a/arch/um/drivers/daemon_kern.c +++ b/arch/um/drivers/daemon_kern.c | |||
@@ -39,20 +39,15 @@ static void daemon_init(struct net_device *dev, void *data) | |||
39 | printk("\n"); | 39 | printk("\n"); |
40 | } | 40 | } |
41 | 41 | ||
42 | static int daemon_read(int fd, struct sk_buff **skb, | 42 | static int daemon_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
43 | struct uml_net_private *lp) | ||
44 | { | 43 | { |
45 | *skb = ether_adjust_skb(*skb, ETH_HEADER_OTHER); | 44 | return net_recvfrom(fd, skb_mac_header(skb), |
46 | if (*skb == NULL) | 45 | skb->dev->mtu + ETH_HEADER_OTHER); |
47 | return -ENOMEM; | ||
48 | return net_recvfrom(fd, skb_mac_header(*skb), | ||
49 | (*skb)->dev->mtu + ETH_HEADER_OTHER); | ||
50 | } | 46 | } |
51 | 47 | ||
52 | static int daemon_write(int fd, struct sk_buff **skb, | 48 | static int daemon_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
53 | struct uml_net_private *lp) | ||
54 | { | 49 | { |
55 | return daemon_user_write(fd, (*skb)->data, (*skb)->len, | 50 | return daemon_user_write(fd, skb->data, skb->len, |
56 | (struct daemon_data *) &lp->user); | 51 | (struct daemon_data *) &lp->user); |
57 | } | 52 | } |
58 | 53 | ||
diff --git a/arch/um/drivers/daemon_user.c b/arch/um/drivers/daemon_user.c index 90983d480ac6..f23c109a055c 100644 --- a/arch/um/drivers/daemon_user.c +++ b/arch/um/drivers/daemon_user.c | |||
@@ -19,8 +19,6 @@ | |||
19 | #include "um_malloc.h" | 19 | #include "um_malloc.h" |
20 | #include "user.h" | 20 | #include "user.h" |
21 | 21 | ||
22 | #define MAX_PACKET (ETH_MAX_PACKET + ETH_HEADER_OTHER) | ||
23 | |||
24 | enum request_type { REQ_NEW_CONTROL }; | 22 | enum request_type { REQ_NEW_CONTROL }; |
25 | 23 | ||
26 | #define SWITCH_MAGIC 0xfeedface | 24 | #define SWITCH_MAGIC 0xfeedface |
@@ -184,18 +182,13 @@ int daemon_user_write(int fd, void *buf, int len, struct daemon_data *pri) | |||
184 | return net_sendto(fd, buf, len, data_addr, sizeof(*data_addr)); | 182 | return net_sendto(fd, buf, len, data_addr, sizeof(*data_addr)); |
185 | } | 183 | } |
186 | 184 | ||
187 | static int daemon_set_mtu(int mtu, void *data) | ||
188 | { | ||
189 | return mtu; | ||
190 | } | ||
191 | |||
192 | const struct net_user_info daemon_user_info = { | 185 | const struct net_user_info daemon_user_info = { |
193 | .init = daemon_user_init, | 186 | .init = daemon_user_init, |
194 | .open = daemon_open, | 187 | .open = daemon_open, |
195 | .close = NULL, | 188 | .close = NULL, |
196 | .remove = daemon_remove, | 189 | .remove = daemon_remove, |
197 | .set_mtu = daemon_set_mtu, | ||
198 | .add_address = NULL, | 190 | .add_address = NULL, |
199 | .delete_address = NULL, | 191 | .delete_address = NULL, |
200 | .max_packet = MAX_PACKET - ETH_HEADER_OTHER | 192 | .mtu = ETH_MAX_PACKET, |
193 | .max_packet = ETH_MAX_PACKET + ETH_HEADER_OTHER, | ||
201 | }; | 194 | }; |
diff --git a/arch/um/drivers/mcast_kern.c b/arch/um/drivers/mcast_kern.c index 5027b870d11d..822092f149be 100644 --- a/arch/um/drivers/mcast_kern.c +++ b/arch/um/drivers/mcast_kern.c | |||
@@ -39,18 +39,15 @@ static void mcast_init(struct net_device *dev, void *data) | |||
39 | dpri->addr, dpri->port, dpri->ttl); | 39 | dpri->addr, dpri->port, dpri->ttl); |
40 | } | 40 | } |
41 | 41 | ||
42 | static int mcast_read(int fd, struct sk_buff **skb, struct uml_net_private *lp) | 42 | static int mcast_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
43 | { | 43 | { |
44 | *skb = ether_adjust_skb(*skb, ETH_HEADER_OTHER); | 44 | return net_recvfrom(fd, skb_mac_header(skb), |
45 | if (*skb == NULL) | 45 | skb->dev->mtu + ETH_HEADER_OTHER); |
46 | return -ENOMEM; | ||
47 | return net_recvfrom(fd, skb_mac_header(*skb), | ||
48 | (*skb)->dev->mtu + ETH_HEADER_OTHER); | ||
49 | } | 46 | } |
50 | 47 | ||
51 | static int mcast_write(int fd, struct sk_buff **skb, struct uml_net_private *lp) | 48 | static int mcast_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
52 | { | 49 | { |
53 | return mcast_user_write(fd, (*skb)->data, (*skb)->len, | 50 | return mcast_user_write(fd, skb->data, skb->len, |
54 | (struct mcast_data *) &lp->user); | 51 | (struct mcast_data *) &lp->user); |
55 | } | 52 | } |
56 | 53 | ||
diff --git a/arch/um/drivers/mcast_user.c b/arch/um/drivers/mcast_user.c index e427b5322a36..5f647d7a7292 100644 --- a/arch/um/drivers/mcast_user.c +++ b/arch/um/drivers/mcast_user.c | |||
@@ -20,8 +20,6 @@ | |||
20 | #include "um_malloc.h" | 20 | #include "um_malloc.h" |
21 | #include "user.h" | 21 | #include "user.h" |
22 | 22 | ||
23 | #define MAX_PACKET (ETH_MAX_PACKET + ETH_HEADER_OTHER) | ||
24 | |||
25 | static struct sockaddr_in *new_addr(char *addr, unsigned short port) | 23 | static struct sockaddr_in *new_addr(char *addr, unsigned short port) |
26 | { | 24 | { |
27 | struct sockaddr_in *sin; | 25 | struct sockaddr_in *sin; |
@@ -154,18 +152,13 @@ int mcast_user_write(int fd, void *buf, int len, struct mcast_data *pri) | |||
154 | return net_sendto(fd, buf, len, data_addr, sizeof(*data_addr)); | 152 | return net_sendto(fd, buf, len, data_addr, sizeof(*data_addr)); |
155 | } | 153 | } |
156 | 154 | ||
157 | static int mcast_set_mtu(int mtu, void *data) | ||
158 | { | ||
159 | return mtu; | ||
160 | } | ||
161 | |||
162 | const struct net_user_info mcast_user_info = { | 155 | const struct net_user_info mcast_user_info = { |
163 | .init = mcast_user_init, | 156 | .init = mcast_user_init, |
164 | .open = mcast_open, | 157 | .open = mcast_open, |
165 | .close = mcast_close, | 158 | .close = mcast_close, |
166 | .remove = mcast_remove, | 159 | .remove = mcast_remove, |
167 | .set_mtu = mcast_set_mtu, | ||
168 | .add_address = NULL, | 160 | .add_address = NULL, |
169 | .delete_address = NULL, | 161 | .delete_address = NULL, |
170 | .max_packet = MAX_PACKET - ETH_HEADER_OTHER | 162 | .mtu = ETH_MAX_PACKET, |
163 | .max_packet = ETH_MAX_PACKET + ETH_HEADER_OTHER, | ||
171 | }; | 164 | }; |
diff --git a/arch/um/drivers/net_kern.c b/arch/um/drivers/net_kern.c index b097a24c1496..59811cc880e0 100644 --- a/arch/um/drivers/net_kern.c +++ b/arch/um/drivers/net_kern.c | |||
@@ -41,16 +41,16 @@ static int uml_net_rx(struct net_device *dev) | |||
41 | struct sk_buff *skb; | 41 | struct sk_buff *skb; |
42 | 42 | ||
43 | /* If we can't allocate memory, try again next round. */ | 43 | /* If we can't allocate memory, try again next round. */ |
44 | skb = dev_alloc_skb(dev->mtu); | 44 | skb = dev_alloc_skb(lp->max_packet); |
45 | if (skb == NULL) { | 45 | if (skb == NULL) { |
46 | lp->stats.rx_dropped++; | 46 | lp->stats.rx_dropped++; |
47 | return 0; | 47 | return 0; |
48 | } | 48 | } |
49 | 49 | ||
50 | skb->dev = dev; | 50 | skb->dev = dev; |
51 | skb_put(skb, dev->mtu); | 51 | skb_put(skb, lp->max_packet); |
52 | skb_reset_mac_header(skb); | 52 | skb_reset_mac_header(skb); |
53 | pkt_len = (*lp->read)(lp->fd, &skb, lp); | 53 | pkt_len = (*lp->read)(lp->fd, skb, lp); |
54 | 54 | ||
55 | if (pkt_len > 0) { | 55 | if (pkt_len > 0) { |
56 | skb_trim(skb, pkt_len); | 56 | skb_trim(skb, pkt_len); |
@@ -178,7 +178,7 @@ static int uml_net_start_xmit(struct sk_buff *skb, struct net_device *dev) | |||
178 | 178 | ||
179 | spin_lock_irqsave(&lp->lock, flags); | 179 | spin_lock_irqsave(&lp->lock, flags); |
180 | 180 | ||
181 | len = (*lp->write)(lp->fd, &skb, lp); | 181 | len = (*lp->write)(lp->fd, skb, lp); |
182 | 182 | ||
183 | if (len == skb->len) { | 183 | if (len == skb->len) { |
184 | lp->stats.tx_packets++; | 184 | lp->stats.tx_packets++; |
@@ -240,22 +240,9 @@ static int uml_net_set_mac(struct net_device *dev, void *addr) | |||
240 | 240 | ||
241 | static int uml_net_change_mtu(struct net_device *dev, int new_mtu) | 241 | static int uml_net_change_mtu(struct net_device *dev, int new_mtu) |
242 | { | 242 | { |
243 | struct uml_net_private *lp = dev->priv; | ||
244 | int err = 0; | ||
245 | |||
246 | spin_lock_irq(&lp->lock); | ||
247 | |||
248 | new_mtu = (*lp->set_mtu)(new_mtu, &lp->user); | ||
249 | if (new_mtu < 0) { | ||
250 | err = new_mtu; | ||
251 | goto out; | ||
252 | } | ||
253 | |||
254 | dev->mtu = new_mtu; | 243 | dev->mtu = new_mtu; |
255 | 244 | ||
256 | out: | 245 | return 0; |
257 | spin_unlock_irq(&lp->lock); | ||
258 | return err; | ||
259 | } | 246 | } |
260 | 247 | ||
261 | static void uml_net_get_drvinfo(struct net_device *dev, | 248 | static void uml_net_get_drvinfo(struct net_device *dev, |
@@ -427,6 +414,7 @@ static void eth_configure(int n, void *init, char *mac, | |||
427 | .dev = dev, | 414 | .dev = dev, |
428 | .fd = -1, | 415 | .fd = -1, |
429 | .mac = { 0xfe, 0xfd, 0x0, 0x0, 0x0, 0x0}, | 416 | .mac = { 0xfe, 0xfd, 0x0, 0x0, 0x0, 0x0}, |
417 | .max_packet = transport->user->max_packet, | ||
430 | .protocol = transport->kern->protocol, | 418 | .protocol = transport->kern->protocol, |
431 | .open = transport->user->open, | 419 | .open = transport->user->open, |
432 | .close = transport->user->close, | 420 | .close = transport->user->close, |
@@ -434,8 +422,7 @@ static void eth_configure(int n, void *init, char *mac, | |||
434 | .read = transport->kern->read, | 422 | .read = transport->kern->read, |
435 | .write = transport->kern->write, | 423 | .write = transport->kern->write, |
436 | .add_address = transport->user->add_address, | 424 | .add_address = transport->user->add_address, |
437 | .delete_address = transport->user->delete_address, | 425 | .delete_address = transport->user->delete_address }); |
438 | .set_mtu = transport->user->set_mtu }); | ||
439 | 426 | ||
440 | init_timer(&lp->tl); | 427 | init_timer(&lp->tl); |
441 | spin_lock_init(&lp->lock); | 428 | spin_lock_init(&lp->lock); |
@@ -447,7 +434,7 @@ static void eth_configure(int n, void *init, char *mac, | |||
447 | goto out_unregister; | 434 | goto out_unregister; |
448 | 435 | ||
449 | set_ether_mac(dev, device->mac); | 436 | set_ether_mac(dev, device->mac); |
450 | dev->mtu = transport->user->max_packet; | 437 | dev->mtu = transport->user->mtu; |
451 | dev->open = uml_net_open; | 438 | dev->open = uml_net_open; |
452 | dev->hard_start_xmit = uml_net_start_xmit; | 439 | dev->hard_start_xmit = uml_net_start_xmit; |
453 | dev->stop = uml_net_close; | 440 | dev->stop = uml_net_close; |
@@ -807,19 +794,6 @@ static void close_devices(void) | |||
807 | 794 | ||
808 | __uml_exitcall(close_devices); | 795 | __uml_exitcall(close_devices); |
809 | 796 | ||
810 | struct sk_buff *ether_adjust_skb(struct sk_buff *skb, int extra) | ||
811 | { | ||
812 | if ((skb != NULL) && (skb_tailroom(skb) < extra)) { | ||
813 | struct sk_buff *skb2; | ||
814 | |||
815 | skb2 = skb_copy_expand(skb, 0, extra, GFP_ATOMIC); | ||
816 | dev_kfree_skb(skb); | ||
817 | skb = skb2; | ||
818 | } | ||
819 | if (skb != NULL) skb_put(skb, extra); | ||
820 | return skb; | ||
821 | } | ||
822 | |||
823 | void iter_addresses(void *d, void (*cb)(unsigned char *, unsigned char *, | 797 | void iter_addresses(void *d, void (*cb)(unsigned char *, unsigned char *, |
824 | void *), | 798 | void *), |
825 | void *arg) | 799 | void *arg) |
diff --git a/arch/um/drivers/pcap_kern.c b/arch/um/drivers/pcap_kern.c index da0403efbc0d..3a750dd39be1 100644 --- a/arch/um/drivers/pcap_kern.c +++ b/arch/um/drivers/pcap_kern.c | |||
@@ -31,19 +31,14 @@ void pcap_init(struct net_device *dev, void *data) | |||
31 | printk("pcap backend, host interface %s\n", ppri->host_if); | 31 | printk("pcap backend, host interface %s\n", ppri->host_if); |
32 | } | 32 | } |
33 | 33 | ||
34 | static int pcap_read(int fd, struct sk_buff **skb, | 34 | static int pcap_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
35 | struct uml_net_private *lp) | ||
36 | { | 35 | { |
37 | *skb = ether_adjust_skb(*skb, ETH_HEADER_OTHER); | 36 | return pcap_user_read(fd, skb_mac_header(skb), |
38 | if (*skb == NULL) | 37 | skb->dev->mtu + ETH_HEADER_OTHER, |
39 | return -ENOMEM; | ||
40 | |||
41 | return pcap_user_read(fd, skb_mac_header(*skb), | ||
42 | (*skb)->dev->mtu + ETH_HEADER_OTHER, | ||
43 | (struct pcap_data *) &lp->user); | 38 | (struct pcap_data *) &lp->user); |
44 | } | 39 | } |
45 | 40 | ||
46 | static int pcap_write(int fd, struct sk_buff **skb, struct uml_net_private *lp) | 41 | static int pcap_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
47 | { | 42 | { |
48 | return -EPERM; | 43 | return -EPERM; |
49 | } | 44 | } |
diff --git a/arch/um/drivers/pcap_user.c b/arch/um/drivers/pcap_user.c index cf996b82af56..e9809356c530 100644 --- a/arch/um/drivers/pcap_user.c +++ b/arch/um/drivers/pcap_user.c | |||
@@ -13,8 +13,6 @@ | |||
13 | #include "um_malloc.h" | 13 | #include "um_malloc.h" |
14 | #include "user.h" | 14 | #include "user.h" |
15 | 15 | ||
16 | #define MAX_PACKET (ETH_MAX_PACKET + ETH_HEADER_OTHER) | ||
17 | |||
18 | #define PCAP_FD(p) (*(int *)(p)) | 16 | #define PCAP_FD(p) (*(int *)(p)) |
19 | 17 | ||
20 | static int pcap_user_init(void *data, void *dev) | 18 | static int pcap_user_init(void *data, void *dev) |
@@ -23,7 +21,8 @@ static int pcap_user_init(void *data, void *dev) | |||
23 | pcap_t *p; | 21 | pcap_t *p; |
24 | char errors[PCAP_ERRBUF_SIZE]; | 22 | char errors[PCAP_ERRBUF_SIZE]; |
25 | 23 | ||
26 | p = pcap_open_live(pri->host_if, MAX_PACKET, pri->promisc, 0, errors); | 24 | p = pcap_open_live(pri->host_if, ETH_MAX_PACKET + ETH_HEADER_OTHER, |
25 | pri->promisc, 0, errors); | ||
27 | if (p == NULL) { | 26 | if (p == NULL) { |
28 | printk(UM_KERN_ERR "pcap_user_init : pcap_open_live failed - " | 27 | printk(UM_KERN_ERR "pcap_user_init : pcap_open_live failed - " |
29 | "'%s'\n", errors); | 28 | "'%s'\n", errors); |
@@ -133,8 +132,8 @@ const struct net_user_info pcap_user_info = { | |||
133 | .open = pcap_open, | 132 | .open = pcap_open, |
134 | .close = NULL, | 133 | .close = NULL, |
135 | .remove = pcap_remove, | 134 | .remove = pcap_remove, |
136 | .set_mtu = NULL, | ||
137 | .add_address = NULL, | 135 | .add_address = NULL, |
138 | .delete_address = NULL, | 136 | .delete_address = NULL, |
139 | .max_packet = MAX_PACKET - ETH_HEADER_OTHER | 137 | .mtu = ETH_MAX_PACKET, |
138 | .max_packet = ETH_MAX_PACKET + ETH_HEADER_OTHER, | ||
140 | }; | 139 | }; |
diff --git a/arch/um/drivers/slip_kern.c b/arch/um/drivers/slip_kern.c index 05ed351de6b5..ae67e7158e71 100644 --- a/arch/um/drivers/slip_kern.c +++ b/arch/um/drivers/slip_kern.c | |||
@@ -47,17 +47,15 @@ static unsigned short slip_protocol(struct sk_buff *skbuff) | |||
47 | return htons(ETH_P_IP); | 47 | return htons(ETH_P_IP); |
48 | } | 48 | } |
49 | 49 | ||
50 | static int slip_read(int fd, struct sk_buff **skb, | 50 | static int slip_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
51 | struct uml_net_private *lp) | ||
52 | { | 51 | { |
53 | return slip_user_read(fd, skb_mac_header(*skb), (*skb)->dev->mtu, | 52 | return slip_user_read(fd, skb_mac_header(skb), skb->dev->mtu, |
54 | (struct slip_data *) &lp->user); | 53 | (struct slip_data *) &lp->user); |
55 | } | 54 | } |
56 | 55 | ||
57 | static int slip_write(int fd, struct sk_buff **skb, | 56 | static int slip_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
58 | struct uml_net_private *lp) | ||
59 | { | 57 | { |
60 | return slip_user_write(fd, (*skb)->data, (*skb)->len, | 58 | return slip_user_write(fd, skb->data, skb->len, |
61 | (struct slip_data *) &lp->user); | 59 | (struct slip_data *) &lp->user); |
62 | } | 60 | } |
63 | 61 | ||
diff --git a/arch/um/drivers/slip_user.c b/arch/um/drivers/slip_user.c index d78f324e7298..5f06204d6871 100644 --- a/arch/um/drivers/slip_user.c +++ b/arch/um/drivers/slip_user.c | |||
@@ -230,11 +230,6 @@ int slip_user_write(int fd, void *buf, int len, struct slip_data *pri) | |||
230 | return slip_proto_write(fd, buf, len, &pri->slip); | 230 | return slip_proto_write(fd, buf, len, &pri->slip); |
231 | } | 231 | } |
232 | 232 | ||
233 | static int slip_set_mtu(int mtu, void *data) | ||
234 | { | ||
235 | return mtu; | ||
236 | } | ||
237 | |||
238 | static void slip_add_addr(unsigned char *addr, unsigned char *netmask, | 233 | static void slip_add_addr(unsigned char *addr, unsigned char *netmask, |
239 | void *data) | 234 | void *data) |
240 | { | 235 | { |
@@ -260,8 +255,8 @@ const struct net_user_info slip_user_info = { | |||
260 | .open = slip_open, | 255 | .open = slip_open, |
261 | .close = slip_close, | 256 | .close = slip_close, |
262 | .remove = NULL, | 257 | .remove = NULL, |
263 | .set_mtu = slip_set_mtu, | ||
264 | .add_address = slip_add_addr, | 258 | .add_address = slip_add_addr, |
265 | .delete_address = slip_del_addr, | 259 | .delete_address = slip_del_addr, |
266 | .max_packet = BUF_SIZE | 260 | .mtu = BUF_SIZE, |
261 | .max_packet = BUF_SIZE, | ||
267 | }; | 262 | }; |
diff --git a/arch/um/drivers/slirp_kern.c b/arch/um/drivers/slirp_kern.c index b208d5e4a405..240ee650865d 100644 --- a/arch/um/drivers/slirp_kern.c +++ b/arch/um/drivers/slirp_kern.c | |||
@@ -52,18 +52,16 @@ static unsigned short slirp_protocol(struct sk_buff *skbuff) | |||
52 | return htons(ETH_P_IP); | 52 | return htons(ETH_P_IP); |
53 | } | 53 | } |
54 | 54 | ||
55 | static int slirp_read(int fd, struct sk_buff **skb, | 55 | static int slirp_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
56 | struct uml_net_private *lp) | ||
57 | { | 56 | { |
58 | return slirp_user_read(fd, skb_mac_header(*skb), (*skb)->dev->mtu, | 57 | return slirp_user_read(fd, skb_mac_header(skb), skb->dev->mtu, |
59 | (struct slirp_data *) &lp->user); | 58 | (struct slirp_data *) &lp->user); |
60 | } | 59 | } |
61 | 60 | ||
62 | static int slirp_write(int fd, struct sk_buff **skb, | 61 | static int slirp_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
63 | struct uml_net_private *lp) | ||
64 | { | 62 | { |
65 | return slirp_user_write(fd, (*skb)->data, (*skb)->len, | 63 | return slirp_user_write(fd, skb->data, skb->len, |
66 | (struct slirp_data *) &lp->user); | 64 | (struct slirp_data *) &lp->user); |
67 | } | 65 | } |
68 | 66 | ||
69 | const struct net_kern_info slirp_kern_info = { | 67 | const struct net_kern_info slirp_kern_info = { |
diff --git a/arch/um/drivers/slirp_user.c b/arch/um/drivers/slirp_user.c index a4755bc33e1e..1865089ff41a 100644 --- a/arch/um/drivers/slirp_user.c +++ b/arch/um/drivers/slirp_user.c | |||
@@ -124,18 +124,13 @@ int slirp_user_write(int fd, void *buf, int len, struct slirp_data *pri) | |||
124 | return slip_proto_write(fd, buf, len, &pri->slip); | 124 | return slip_proto_write(fd, buf, len, &pri->slip); |
125 | } | 125 | } |
126 | 126 | ||
127 | static int slirp_set_mtu(int mtu, void *data) | ||
128 | { | ||
129 | return mtu; | ||
130 | } | ||
131 | |||
132 | const struct net_user_info slirp_user_info = { | 127 | const struct net_user_info slirp_user_info = { |
133 | .init = slirp_user_init, | 128 | .init = slirp_user_init, |
134 | .open = slirp_open, | 129 | .open = slirp_open, |
135 | .close = slirp_close, | 130 | .close = slirp_close, |
136 | .remove = NULL, | 131 | .remove = NULL, |
137 | .set_mtu = slirp_set_mtu, | ||
138 | .add_address = NULL, | 132 | .add_address = NULL, |
139 | .delete_address = NULL, | 133 | .delete_address = NULL, |
140 | .max_packet = BUF_SIZE | 134 | .mtu = BUF_SIZE, |
135 | .max_packet = BUF_SIZE, | ||
141 | }; | 136 | }; |
diff --git a/arch/um/drivers/vde_kern.c b/arch/um/drivers/vde_kern.c index c5d01685d2b5..add7e722defb 100644 --- a/arch/um/drivers/vde_kern.c +++ b/arch/um/drivers/vde_kern.c | |||
@@ -36,30 +36,25 @@ static void vde_init(struct net_device *dev, void *data) | |||
36 | printk("\n"); | 36 | printk("\n"); |
37 | } | 37 | } |
38 | 38 | ||
39 | static int vde_read(int fd, struct sk_buff **skb, struct uml_net_private *lp) | 39 | static int vde_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
40 | { | 40 | { |
41 | struct vde_data *pri = (struct vde_data *) &lp->user; | 41 | struct vde_data *pri = (struct vde_data *) &lp->user; |
42 | 42 | ||
43 | if (pri->conn != NULL) { | 43 | if (pri->conn != NULL) |
44 | *skb = ether_adjust_skb(*skb, ETH_HEADER_OTHER); | 44 | return vde_user_read(pri->conn, skb_mac_header(skb), |
45 | if (*skb == NULL) | 45 | skb->dev->mtu + ETH_HEADER_OTHER); |
46 | return -ENOMEM; | ||
47 | |||
48 | return vde_user_read(pri->conn, skb_mac_header(*skb), | ||
49 | (*skb)->dev->mtu + ETH_HEADER_OTHER); | ||
50 | } | ||
51 | 46 | ||
52 | printk(KERN_ERR "vde_read - we have no VDECONN to read from"); | 47 | printk(KERN_ERR "vde_read - we have no VDECONN to read from"); |
53 | return -EBADF; | 48 | return -EBADF; |
54 | } | 49 | } |
55 | 50 | ||
56 | static int vde_write(int fd, struct sk_buff **skb, struct uml_net_private *lp) | 51 | static int vde_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
57 | { | 52 | { |
58 | struct vde_data *pri = (struct vde_data *) &lp->user; | 53 | struct vde_data *pri = (struct vde_data *) &lp->user; |
59 | 54 | ||
60 | if (pri->conn != NULL) | 55 | if (pri->conn != NULL) |
61 | return vde_user_write((void *)pri->conn, (*skb)->data, | 56 | return vde_user_write((void *)pri->conn, skb->data, |
62 | (*skb)->len); | 57 | skb->len); |
63 | 58 | ||
64 | printk(KERN_ERR "vde_write - we have no VDECONN to write to"); | 59 | printk(KERN_ERR "vde_write - we have no VDECONN to write to"); |
65 | return -EBADF; | 60 | return -EBADF; |
diff --git a/arch/um/drivers/vde_user.c b/arch/um/drivers/vde_user.c index 7533cd3cbba4..d9941fe5f931 100644 --- a/arch/um/drivers/vde_user.c +++ b/arch/um/drivers/vde_user.c | |||
@@ -12,8 +12,6 @@ | |||
12 | #include "user.h" | 12 | #include "user.h" |
13 | #include "vde.h" | 13 | #include "vde.h" |
14 | 14 | ||
15 | #define MAX_PACKET (ETH_MAX_PACKET + ETH_HEADER_OTHER) | ||
16 | |||
17 | static int vde_user_init(void *data, void *dev) | 15 | static int vde_user_init(void *data, void *dev) |
18 | { | 16 | { |
19 | struct vde_data *pri = data; | 17 | struct vde_data *pri = data; |
@@ -65,20 +63,15 @@ static void vde_remove(void *data) | |||
65 | printk(UM_KERN_WARNING "vde_remove - we have no VDECONN to remove"); | 63 | printk(UM_KERN_WARNING "vde_remove - we have no VDECONN to remove"); |
66 | } | 64 | } |
67 | 65 | ||
68 | static int vde_set_mtu(int mtu, void *data) | ||
69 | { | ||
70 | return mtu; | ||
71 | } | ||
72 | |||
73 | const struct net_user_info vde_user_info = { | 66 | const struct net_user_info vde_user_info = { |
74 | .init = vde_user_init, | 67 | .init = vde_user_init, |
75 | .open = vde_user_open, | 68 | .open = vde_user_open, |
76 | .close = NULL, | 69 | .close = NULL, |
77 | .remove = vde_remove, | 70 | .remove = vde_remove, |
78 | .set_mtu = vde_set_mtu, | ||
79 | .add_address = NULL, | 71 | .add_address = NULL, |
80 | .delete_address = NULL, | 72 | .delete_address = NULL, |
81 | .max_packet = MAX_PACKET - ETH_HEADER_OTHER | 73 | .mtu = ETH_MAX_PACKET, |
74 | .max_packet = ETH_MAX_PACKET + ETH_HEADER_OTHER, | ||
82 | }; | 75 | }; |
83 | 76 | ||
84 | void vde_init_libstuff(struct vde_data *vpri, struct vde_init *init) | 77 | void vde_init_libstuff(struct vde_data *vpri, struct vde_init *init) |
diff --git a/arch/um/include/net_kern.h b/arch/um/include/net_kern.h index 9237056b9103..d843c7924a7c 100644 --- a/arch/um/include/net_kern.h +++ b/arch/um/include/net_kern.h | |||
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) | 2 | * Copyright (C) 2002 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com) |
3 | * Licensed under the GPL | 3 | * Licensed under the GPL |
4 | */ | 4 | */ |
5 | 5 | ||
@@ -30,24 +30,24 @@ struct uml_net_private { | |||
30 | struct work_struct work; | 30 | struct work_struct work; |
31 | int fd; | 31 | int fd; |
32 | unsigned char mac[ETH_ALEN]; | 32 | unsigned char mac[ETH_ALEN]; |
33 | int max_packet; | ||
33 | unsigned short (*protocol)(struct sk_buff *); | 34 | unsigned short (*protocol)(struct sk_buff *); |
34 | int (*open)(void *); | 35 | int (*open)(void *); |
35 | void (*close)(int, void *); | 36 | void (*close)(int, void *); |
36 | void (*remove)(void *); | 37 | void (*remove)(void *); |
37 | int (*read)(int, struct sk_buff **skb, struct uml_net_private *); | 38 | int (*read)(int, struct sk_buff *skb, struct uml_net_private *); |
38 | int (*write)(int, struct sk_buff **skb, struct uml_net_private *); | 39 | int (*write)(int, struct sk_buff *skb, struct uml_net_private *); |
39 | 40 | ||
40 | void (*add_address)(unsigned char *, unsigned char *, void *); | 41 | void (*add_address)(unsigned char *, unsigned char *, void *); |
41 | void (*delete_address)(unsigned char *, unsigned char *, void *); | 42 | void (*delete_address)(unsigned char *, unsigned char *, void *); |
42 | int (*set_mtu)(int mtu, void *); | ||
43 | char user[0]; | 43 | char user[0]; |
44 | }; | 44 | }; |
45 | 45 | ||
46 | struct net_kern_info { | 46 | struct net_kern_info { |
47 | void (*init)(struct net_device *, void *); | 47 | void (*init)(struct net_device *, void *); |
48 | unsigned short (*protocol)(struct sk_buff *); | 48 | unsigned short (*protocol)(struct sk_buff *); |
49 | int (*read)(int, struct sk_buff **skb, struct uml_net_private *); | 49 | int (*read)(int, struct sk_buff *skb, struct uml_net_private *); |
50 | int (*write)(int, struct sk_buff **skb, struct uml_net_private *); | 50 | int (*write)(int, struct sk_buff *skb, struct uml_net_private *); |
51 | }; | 51 | }; |
52 | 52 | ||
53 | struct transport { | 53 | struct transport { |
@@ -62,7 +62,6 @@ struct transport { | |||
62 | 62 | ||
63 | extern struct net_device *ether_init(int); | 63 | extern struct net_device *ether_init(int); |
64 | extern unsigned short ether_protocol(struct sk_buff *); | 64 | extern unsigned short ether_protocol(struct sk_buff *); |
65 | extern struct sk_buff *ether_adjust_skb(struct sk_buff *skb, int extra); | ||
66 | extern int tap_setup_common(char *str, char *type, char **dev_name, | 65 | extern int tap_setup_common(char *str, char *type, char **dev_name, |
67 | char **mac_out, char **gate_addr); | 66 | char **mac_out, char **gate_addr); |
68 | extern void register_transport(struct transport *new); | 67 | extern void register_transport(struct transport *new); |
diff --git a/arch/um/include/net_user.h b/arch/um/include/net_user.h index cfe7c50634b9..63bee158cd8e 100644 --- a/arch/um/include/net_user.h +++ b/arch/um/include/net_user.h | |||
@@ -1,5 +1,5 @@ | |||
1 | /* | 1 | /* |
2 | * Copyright (C) 2002 Jeff Dike (jdike@karaya.com) | 2 | * Copyright (C) 2002 - 2007 Jeff Dike (jdike@{addtoit,linux.intel}.com) |
3 | * Licensed under the GPL | 3 | * Licensed under the GPL |
4 | */ | 4 | */ |
5 | 5 | ||
@@ -18,10 +18,10 @@ struct net_user_info { | |||
18 | int (*open)(void *); | 18 | int (*open)(void *); |
19 | void (*close)(int, void *); | 19 | void (*close)(int, void *); |
20 | void (*remove)(void *); | 20 | void (*remove)(void *); |
21 | int (*set_mtu)(int mtu, void *); | ||
22 | void (*add_address)(unsigned char *, unsigned char *, void *); | 21 | void (*add_address)(unsigned char *, unsigned char *, void *); |
23 | void (*delete_address)(unsigned char *, unsigned char *, void *); | 22 | void (*delete_address)(unsigned char *, unsigned char *, void *); |
24 | int max_packet; | 23 | int max_packet; |
24 | int mtu; | ||
25 | }; | 25 | }; |
26 | 26 | ||
27 | extern void ether_user_init(void *data, void *dev); | 27 | extern void ether_user_init(void *data, void *dev); |
diff --git a/arch/um/os-Linux/drivers/ethertap_kern.c b/arch/um/os-Linux/drivers/ethertap_kern.c index 542bcc58354c..04f11b9f1ac0 100644 --- a/arch/um/os-Linux/drivers/ethertap_kern.c +++ b/arch/um/os-Linux/drivers/ethertap_kern.c | |||
@@ -36,35 +36,24 @@ static void etap_init(struct net_device *dev, void *data) | |||
36 | printk("\n"); | 36 | printk("\n"); |
37 | } | 37 | } |
38 | 38 | ||
39 | static int etap_read(int fd, struct sk_buff **skb, struct uml_net_private *lp) | 39 | static int etap_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
40 | { | 40 | { |
41 | int len; | 41 | int len; |
42 | 42 | ||
43 | *skb = ether_adjust_skb(*skb, ETH_HEADER_ETHERTAP); | 43 | len = net_recvfrom(fd, skb_mac_header(skb), |
44 | if (*skb == NULL) | 44 | skb->dev->mtu + 2 + ETH_HEADER_ETHERTAP); |
45 | return -ENOMEM; | ||
46 | len = net_recvfrom(fd, skb_mac_header(*skb), | ||
47 | (*skb)->dev->mtu + 2 * ETH_HEADER_ETHERTAP); | ||
48 | if (len <= 0) | 45 | if (len <= 0) |
49 | return len; | 46 | return(len); |
50 | skb_pull(*skb, 2); | 47 | |
48 | skb_pull(skb, 2); | ||
51 | len -= 2; | 49 | len -= 2; |
52 | return len; | 50 | return len; |
53 | } | 51 | } |
54 | 52 | ||
55 | static int etap_write(int fd, struct sk_buff **skb, struct uml_net_private *lp) | 53 | static int etap_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
56 | { | 54 | { |
57 | if (skb_headroom(*skb) < 2) { | 55 | skb_push(skb, 2); |
58 | struct sk_buff *skb2; | 56 | return net_send(fd, skb->data, skb->len); |
59 | |||
60 | skb2 = skb_realloc_headroom(*skb, 2); | ||
61 | dev_kfree_skb(*skb); | ||
62 | if (skb2 == NULL) | ||
63 | return -ENOMEM; | ||
64 | *skb = skb2; | ||
65 | } | ||
66 | skb_push(*skb, 2); | ||
67 | return net_send(fd, (*skb)->data, (*skb)->len); | ||
68 | } | 57 | } |
69 | 58 | ||
70 | const struct net_kern_info ethertap_kern_info = { | 59 | const struct net_kern_info ethertap_kern_info = { |
@@ -99,6 +88,7 @@ static struct transport ethertap_transport = { | |||
99 | .user = ðertap_user_info, | 88 | .user = ðertap_user_info, |
100 | .kern = ðertap_kern_info, | 89 | .kern = ðertap_kern_info, |
101 | .private_size = sizeof(struct ethertap_data), | 90 | .private_size = sizeof(struct ethertap_data), |
91 | .setup_size = sizeof(struct ethertap_init), | ||
102 | }; | 92 | }; |
103 | 93 | ||
104 | static int register_ethertap(void) | 94 | static int register_ethertap(void) |
diff --git a/arch/um/os-Linux/drivers/ethertap_user.c b/arch/um/os-Linux/drivers/ethertap_user.c index 29404b955f18..4ff553603449 100644 --- a/arch/um/os-Linux/drivers/ethertap_user.c +++ b/arch/um/os-Linux/drivers/ethertap_user.c | |||
@@ -222,11 +222,6 @@ static void etap_close(int fd, void *data) | |||
222 | pri->control_fd = -1; | 222 | pri->control_fd = -1; |
223 | } | 223 | } |
224 | 224 | ||
225 | static int etap_set_mtu(int mtu, void *data) | ||
226 | { | ||
227 | return mtu; | ||
228 | } | ||
229 | |||
230 | static void etap_add_addr(unsigned char *addr, unsigned char *netmask, | 225 | static void etap_add_addr(unsigned char *addr, unsigned char *netmask, |
231 | void *data) | 226 | void *data) |
232 | { | 227 | { |
@@ -254,8 +249,8 @@ const struct net_user_info ethertap_user_info = { | |||
254 | .open = etap_open, | 249 | .open = etap_open, |
255 | .close = etap_close, | 250 | .close = etap_close, |
256 | .remove = NULL, | 251 | .remove = NULL, |
257 | .set_mtu = etap_set_mtu, | ||
258 | .add_address = etap_add_addr, | 252 | .add_address = etap_add_addr, |
259 | .delete_address = etap_del_addr, | 253 | .delete_address = etap_del_addr, |
260 | .max_packet = MAX_PACKET - ETH_HEADER_ETHERTAP | 254 | .mtu = ETH_MAX_PACKET, |
255 | .max_packet = ETH_MAX_PACKET + ETH_HEADER_ETHERTAP, | ||
261 | }; | 256 | }; |
diff --git a/arch/um/os-Linux/drivers/tuntap_kern.c b/arch/um/os-Linux/drivers/tuntap_kern.c index 9ade1f892ac8..9d384807b077 100644 --- a/arch/um/os-Linux/drivers/tuntap_kern.c +++ b/arch/um/os-Linux/drivers/tuntap_kern.c | |||
@@ -35,20 +35,15 @@ static void tuntap_init(struct net_device *dev, void *data) | |||
35 | printk("\n"); | 35 | printk("\n"); |
36 | } | 36 | } |
37 | 37 | ||
38 | static int tuntap_read(int fd, struct sk_buff **skb, | 38 | static int tuntap_read(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
39 | struct uml_net_private *lp) | ||
40 | { | 39 | { |
41 | *skb = ether_adjust_skb(*skb, ETH_HEADER_OTHER); | 40 | return net_read(fd, skb_mac_header(skb), |
42 | if (*skb == NULL) | 41 | skb->dev->mtu + ETH_HEADER_OTHER); |
43 | return -ENOMEM; | ||
44 | return net_read(fd, skb_mac_header(*skb), | ||
45 | (*skb)->dev->mtu + ETH_HEADER_OTHER); | ||
46 | } | 42 | } |
47 | 43 | ||
48 | static int tuntap_write(int fd, struct sk_buff **skb, | 44 | static int tuntap_write(int fd, struct sk_buff *skb, struct uml_net_private *lp) |
49 | struct uml_net_private *lp) | ||
50 | { | 45 | { |
51 | return net_write(fd, (*skb)->data, (*skb)->len); | 46 | return net_write(fd, skb->data, skb->len); |
52 | } | 47 | } |
53 | 48 | ||
54 | const struct net_kern_info tuntap_kern_info = { | 49 | const struct net_kern_info tuntap_kern_info = { |
diff --git a/arch/um/os-Linux/drivers/tuntap_user.c b/arch/um/os-Linux/drivers/tuntap_user.c index 10714a413cfd..6c55d3c8ead8 100644 --- a/arch/um/os-Linux/drivers/tuntap_user.c +++ b/arch/um/os-Linux/drivers/tuntap_user.c | |||
@@ -18,8 +18,6 @@ | |||
18 | #include "tuntap.h" | 18 | #include "tuntap.h" |
19 | #include "user.h" | 19 | #include "user.h" |
20 | 20 | ||
21 | #define MAX_PACKET ETH_MAX_PACKET | ||
22 | |||
23 | static int tuntap_user_init(void *data, void *dev) | 21 | static int tuntap_user_init(void *data, void *dev) |
24 | { | 22 | { |
25 | struct tuntap_data *pri = data; | 23 | struct tuntap_data *pri = data; |
@@ -206,18 +204,13 @@ static void tuntap_close(int fd, void *data) | |||
206 | pri->fd = -1; | 204 | pri->fd = -1; |
207 | } | 205 | } |
208 | 206 | ||
209 | static int tuntap_set_mtu(int mtu, void *data) | ||
210 | { | ||
211 | return mtu; | ||
212 | } | ||
213 | |||
214 | const struct net_user_info tuntap_user_info = { | 207 | const struct net_user_info tuntap_user_info = { |
215 | .init = tuntap_user_init, | 208 | .init = tuntap_user_init, |
216 | .open = tuntap_open, | 209 | .open = tuntap_open, |
217 | .close = tuntap_close, | 210 | .close = tuntap_close, |
218 | .remove = NULL, | 211 | .remove = NULL, |
219 | .set_mtu = tuntap_set_mtu, | ||
220 | .add_address = tuntap_add_addr, | 212 | .add_address = tuntap_add_addr, |
221 | .delete_address = tuntap_del_addr, | 213 | .delete_address = tuntap_del_addr, |
222 | .max_packet = MAX_PACKET | 214 | .mtu = ETH_MAX_PACKET, |
215 | .max_packet = ETH_MAX_PACKET + ETH_HEADER_OTHER, | ||
223 | }; | 216 | }; |