19 #include <linux/list.h>
22 #include <linux/slab.h>
24 #include <linux/if_ether.h>
27 #include <linux/if_tun.h>
32 #include <linux/ethtool.h>
33 #include <linux/rtnetlink.h>
38 #define DRIVER_NAME "iss-netdev"
39 #define ETH_MAX_PACKET 1500
40 #define ETH_HEADER_OTHER 14
41 #define ISS_NET_TIMER_VALUE (2 * HZ)
54 #define TRANSPORT_TUNTAP_NAME "tuntap"
55 #define TRANSPORT_TUNTAP_MTU ETH_MAX_PACKET
134 if ((skb !=
NULL) && (skb_tailroom(skb) < extra)) {
150 static void dev_ip_addr(
void *
d,
char *
buf,
char *bin_buf)
154 struct in_ifaddr *
in;
157 if ((ip ==
NULL) || ((in = ip->ifa_list) ==
NULL)) {
162 addr = in->ifa_address;
163 sprintf(buf,
"%d.%d.%d.%d", addr & 0xff, (addr >> 8) & 0xff,
164 (addr >> 16) & 0xff, addr >> 24);
167 bin_buf[0] = addr & 0xff;
168 bin_buf[1] = (addr >> 8) & 0xff;
169 bin_buf[2] = (addr >> 16) & 0xff;
170 bin_buf[3] = addr >> 24;
176 static void inline set_ether_mac(
void *d,
unsigned char *addr)
188 char *dev_name = lp->
tp.info.tuntap.dev_name;
194 if (!lp->
tp.info.tuntap.fixed_config)
197 if ((fd = simc_open(
"/dev/net/tun", 02, 0)) < 0) {
198 printk(
"Failed to open /dev/net/tun, returned %d "
199 "(errno = %d)\n", fd, errno);
203 memset(&ifr, 0,
sizeof ifr);
205 strlcpy(ifr.ifr_name, dev_name,
sizeof ifr.ifr_name);
207 if ((err = simc_ioctl(fd,
TUNSETIFF, (
void*) &ifr)) < 0) {
208 printk(
"Failed to set interface, returned %d "
209 "(errno = %d)\n", err, errno);
214 lp->
tp.info.tuntap.fd =
fd;
221 if (lp->
tp.info.tuntap.fixed_config)
224 simc_close(lp->
tp.info.tuntap.fd);
225 lp->
tp.info.tuntap.fd = -1;
236 return simc_read(lp->
tp.info.tuntap.fd,
242 return simc_write(lp->
tp.info.tuntap.fd, (*skb)->data, (*skb)->len);
252 return simc_poll(lp->
tp.info.tuntap.fd);
272 printk(
"Extra garbage on specification : '%s'\n", rem);
275 }
else if (*init !=
'\0') {
276 printk(
"Invalid argument: %s. Skipping device!\n", init);
281 strncpy(lp->
tp.info.tuntap.dev_name, dev_name,
282 sizeof lp->
tp.info.tuntap.dev_name);
283 lp->
tp.info.tuntap.fixed_config = 1;
289 if (setup_etheraddr(mac_str, lp->
mac))
296 lp->
tp.info.tuntap.fd = -1;
298 lp->
tp.open = tuntap_open;
299 lp->
tp.close = tuntap_close;
300 lp->
tp.read = tuntap_read;
301 lp->
tp.write = tuntap_write;
303 lp->
tp.poll = tuntap_poll;
305 printk(
"TUN/TAP backend - ");
307 if (lp->host.gate_addr !=
NULL)
308 printk(
"IP = %s", lp->host.gate_addr);
325 if (lp->
tp.poll(lp) == 0)
331 lp->
stats.rx_dropped++;
340 skb_reset_mac_header(skb);
341 pkt_len = lp->
tp.read(lp, &skb);
349 lp->
stats.rx_packets++;
363 spin_lock(&opened_lock);
370 if (!netif_running(lp->
dev))
373 spin_lock(&lp->
lock);
375 while ((err = iss_net_rx(lp->
dev)) > 0)
378 spin_unlock(&lp->
lock);
382 "shutting it down\n", lp->
dev->name, err);
389 spin_unlock(&opened_lock);
394 static void iss_net_timer(
unsigned long priv)
398 spin_lock(&lp->
lock);
404 spin_unlock(&lp->
lock);
408 static int iss_net_open(
struct net_device *dev)
411 char addr[
sizeof "255.255.255.255\0"];
414 spin_lock(&lp->
lock);
416 if ((err = lp->
tp.open(lp)) < 0)
420 dev_ip_addr(dev, addr, &lp->
mac[2]);
421 set_ether_mac(dev, lp->
mac);
424 netif_start_queue(dev);
430 while ((err = iss_net_rx(dev)) > 0)
433 spin_lock(&opened_lock);
435 spin_unlock(&opened_lock);
440 lp->
timer.function = iss_net_timer;
444 spin_unlock(&lp->
lock);
448 static int iss_net_close(
struct net_device *dev)
451 printk(
"iss_net_close!\n");
452 netif_stop_queue(dev);
453 spin_lock(&lp->
lock);
455 spin_lock(&opened_lock);
457 spin_unlock(&opened_lock);
463 spin_unlock(&lp->
lock);
473 netif_stop_queue(dev);
476 len = lp->
tp.write(lp, &skb);
478 if (len == skb->
len) {
479 lp->
stats.tx_packets++;
482 netif_start_queue(dev);
485 netif_wake_queue(dev);
487 }
else if (len == 0) {
488 netif_start_queue(dev);
489 lp->
stats.tx_dropped++;
492 netif_start_queue(dev);
496 spin_unlock_irqrestore(&lp->
lock, flags);
509 static void iss_net_set_multicast_list(
struct net_device *dev)
521 static void iss_net_tx_timeout(
struct net_device *dev)
525 netif_wake_queue(dev);
529 static int iss_net_set_mac(
struct net_device *dev,
void *addr)
535 spin_lock(&lp->
lock);
537 spin_unlock(&lp->
lock);
543 static int iss_net_change_mtu(
struct net_device *dev,
int new_mtu)
549 spin_lock(&lp->
lock);
558 spin_unlock(&lp->
lock);
575 static int driver_registered;
578 .ndo_open = iss_net_open,
579 .ndo_stop = iss_net_close,
580 .ndo_get_stats = iss_net_get_stats,
581 .ndo_start_xmit = iss_net_start_xmit,
583 .ndo_change_mtu = iss_net_change_mtu,
584 .ndo_set_mac_address = iss_net_set_mac,
586 .ndo_tx_timeout = iss_net_tx_timeout,
587 .ndo_set_rx_mode = iss_net_set_multicast_list,
590 static int iss_net_configure(
int index,
char *init)
596 if ((dev = alloc_etherdev(
sizeof *lp)) ==
NULL) {
603 lp = netdev_priv(dev);
611 .mac = { 0xfe, 0xfd, 0x0, 0x0, 0x0, 0x0 },
620 if (!tuntap_probe(lp, index, init)) {
621 printk(
"Invalid arguments. Skipping device!\n");
632 if (!driver_registered) {
634 driver_registered = 1;
637 spin_lock(&devices_lock);
639 spin_unlock(&devices_lock);
663 printk(
"Error registering net device!\n");
674 set_ether_mac(dev, lp->
mac);
701 #define ERR KERN_ERR "iss_net_setup: "
703 static int iss_net_setup(
char *
str)
713 printk(
ERR "Failed to parse '%s'\n", str);
717 printk(
ERR "Device %d is negative\n", n);
720 if (*(str = end) !=
'=') {
721 printk(
ERR "Expected '=' after device number\n");
725 spin_lock(&devices_lock);
729 if (device->
index == n)
733 spin_unlock(&devices_lock);
735 if (device && device->
index == n) {
736 printk(
ERR "Device %d already configured\n", n);
741 printk(
"Alloc_bootmem failed\n");
745 INIT_LIST_HEAD(&new->list);
755 __setup(
"eth=", iss_net_setup);
770 iss_net_configure(eth->
index, eth->
init);