ViewVC Help
View File | Revision Log | Show Annotations | Revision Graph | Root Listing
root/cebix/BasiliskII/src/Unix/Linux/NetDriver/sheep_net.c
Revision: 1.17
Committed: 2010-11-27T00:14:09Z (13 years, 7 months ago) by asvitkine
Content type: text/plain
Branch: MAIN
CVS Tags: HEAD
Changes since 1.16: +30 -0 lines
Log Message:
[Amadeusz Sławiński]
Patch fixing build on 2.6.35 and 2.6.36 kernels.

File Contents

# Content
1 /*
2 * sheep_net.c - Linux driver for SheepShaver/Basilisk II networking (access to raw Ethernet packets)
3 *
4 * sheep_net (C) 1999-2004 Mar"c" Hellwig and Christian Bauer
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 */
20 /* modversions.h redefines kernel symbols. Now include other headers */
21 #include <linux/kernel.h>
22 #include <linux/module.h>
23 #include <linux/version.h>
24
25
26 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,35)
27 #define LINUX_26_35
28 #endif
29
30 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,36)
31 #define LINUX_26_36
32 #endif
33
34 /* Compatibility glue */
35 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,30)
36 #define LINUX_26_30
37
38 #else
39
40 /* determine whether to use checksummed versions of kernel symbols */
41 /***
42 #include <linux/config.h>
43 ***/
44 #include "config.h"
45 #include <linux/autoconf.h>
46
47 #if defined(CONFIG_MODVERSIONS) && !defined(MODVERSIONS)
48 #define MODVERSIONS
49 #endif
50
51 #if defined(MODVERSIONS)
52 #include <linux/modversions.h>
53 #endif
54
55 #endif
56
57 #include <linux/types.h>
58 #include <linux/miscdevice.h>
59 #include <linux/netdevice.h>
60 #include <linux/etherdevice.h>
61 #include <linux/if_ether.h>
62 #include <linux/if_arp.h>
63 #include <linux/fs.h>
64 #include <linux/poll.h>
65 #include <linux/init.h>
66 #include <net/sock.h>
67 #include <asm/uaccess.h>
68 #include <asm/ioctls.h>
69 #include <net/arp.h>
70 #include <net/ip.h>
71 #include <net/raw.h>
72 #include <linux/in.h>
73 #include <linux/wait.h>
74
75 MODULE_AUTHOR("Christian Bauer");
76 MODULE_DESCRIPTION("Pseudo ethernet device for emulators");
77
78 /* Compatibility glue */
79 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
80 #define LINUX_26
81 #endif
82 #if LINUX_VERSION_CODE >= KERNEL_VERSION(2,4,0)
83 #define LINUX_24
84 #else
85 #define net_device device
86 typedef struct wait_queue *wait_queue_head_t;
87 #define init_waitqueue_head(x) *(x)=NULL
88 #endif
89 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,9)
90 #define eth_hdr(skb) (skb)->mac.ethernet
91 #define skb_mac_header(skb) (skb)->mac.raw
92 #define ipip_hdr(skb) (skb)->h.ipiph
93 #endif
94
95 #ifdef LINUX_26
96 #define skt_set_dead(skt) do {} while(0)
97 #define wmem_alloc sk_wmem_alloc
98 #else
99 #define skt_set_dead(skt) (skt)->dead = 1
100 #endif
101
102 #define DEBUG 0
103
104 #define bug printk
105 #if DEBUG
106 #define D(x) (x);
107 #else
108 #define D(x) ;
109 #endif
110
111
112 /* Constants */
113 #define SHEEP_NET_MINOR 198 /* Driver minor number */
114 #define MAX_QUEUE 32 /* Maximum number of packets in queue */
115 #define PROT_MAGIC 1520 /* Our "magic" protocol type */
116
117 #define ETH_ADDR_MULTICAST 0x1
118 #define ETH_ADDR_LOCALLY_DEFINED 0x02
119
120 #define SIOC_MOL_GET_IPFILTER SIOCDEVPRIVATE
121 #define SIOC_MOL_SET_IPFILTER (SIOCDEVPRIVATE + 1)
122
123 /* Prototypes */
124 static int sheep_net_open(struct inode *inode, struct file *f);
125 static int sheep_net_release(struct inode *inode, struct file *f);
126 static ssize_t sheep_net_read(struct file *f, char *buf, size_t count, loff_t *off);
127 static ssize_t sheep_net_write(struct file *f, const char *buf, size_t count, loff_t *off);
128 static unsigned int sheep_net_poll(struct file *f, struct poll_table_struct *wait);
129 #ifdef LINUX_26_36
130 static long sheep_net_ioctl(struct file *f, unsigned int code, unsigned long arg);
131 #else
132 static int sheep_net_ioctl(struct inode *inode, struct file *f, unsigned int code, unsigned long arg);
133 #endif
134 #ifdef LINUX_26
135 static int sheep_net_receiver(struct sk_buff *skb, struct net_device *dev, struct packet_type *pt, struct net_device *foo);
136 #else
137 static int sheep_net_receiver(struct sk_buff *skb, struct net_device *dev, struct packet_type *pt);
138 #endif
139
140 /*
141 * Driver private variables
142 */
143
144 struct SheepVars {
145 /* IMPORTANT: the packet_type struct must go first. It no longer
146 (2.6) contains * a data field so we typecast to get the SheepVars
147 struct */
148 struct packet_type pt; /* Receiver packet type */
149 struct net_device *ether; /* The Ethernet device we're attached to */
150 struct sock *skt; /* Socket for communication with Ethernet card */
151 struct sk_buff_head queue; /* Receiver packet queue */
152 wait_queue_head_t wait; /* Wait queue for blocking read operations */
153 u32 ipfilter; /* Only receive IP packets destined for this address (host byte order) */
154 char eth_addr[6]; /* Hardware address of the Ethernet card */
155 char fake_addr[6]; /* Local faked hardware address (what SheepShaver sees) */
156 };
157
158
159 /*
160 * file_operations structure - has function pointers to the
161 * various entry points for device operations
162 */
163
164 static struct file_operations sheep_net_fops = {
165 .owner = THIS_MODULE,
166 .read = sheep_net_read,
167 .write = sheep_net_write,
168 .poll = sheep_net_poll,
169 #ifdef LINUX_26_36
170 .unlocked_ioctl = sheep_net_ioctl,
171 #else
172 .ioctl = sheep_net_ioctl,
173 #endif
174 .open = sheep_net_open,
175 .release = sheep_net_release,
176 };
177
178
179 /*
180 * miscdevice structure for driver initialization
181 */
182
183 static struct miscdevice sheep_net_device = {
184 .minor = SHEEP_NET_MINOR, /* minor number */
185 .name = "sheep_net", /* name */
186 .fops = &sheep_net_fops
187 };
188
189
190 /*
191 * fake protocol to use a common socket
192 */
193 static struct proto sheep_proto = {
194 .name = "SHEEP",
195 .owner = THIS_MODULE,
196 .obj_size = sizeof(struct sock),
197 };
198
199
200 /*
201 * Initialize module
202 */
203
204 int init_module(void)
205 {
206 int ret;
207
208 /* Register driver */
209 ret = misc_register(&sheep_net_device);
210 D(bug("Sheep net driver installed\n"));
211 return ret;
212 }
213
214
215 /*
216 * Deinitialize module
217 */
218
219 void cleanup_module(void)
220 {
221 /* Unregister driver */
222 misc_deregister(&sheep_net_device);
223 D(bug("Sheep net driver removed\n"));
224 }
225
226
227 /*
228 * Driver open() function
229 */
230
231 static int sheep_net_open(struct inode *inode, struct file *f)
232 {
233 struct SheepVars *v;
234 D(bug("sheep_net: open\n"));
235
236 /* Must be opened with read permissions */
237 if ((f->f_flags & O_ACCMODE) == O_WRONLY)
238 return -EPERM;
239
240 /* Allocate private variables */
241 v = (struct SheepVars *)kmalloc(sizeof(struct SheepVars), GFP_USER);
242 if (v == NULL)
243 return -ENOMEM;
244
245 #ifndef LINUX_26_30
246 lock_kernel();
247 #endif
248 memset(v, 0, sizeof(struct SheepVars));
249 skb_queue_head_init(&v->queue);
250 init_waitqueue_head(&v->wait);
251 v->fake_addr[0] = 0xfe;
252 v->fake_addr[1] = 0xfd;
253 v->fake_addr[2] = 0xde;
254 v->fake_addr[3] = 0xad;
255 v->fake_addr[4] = 0xbe;
256 v->fake_addr[5] = 0xef;
257
258 /* Put our stuff where we will be able to find it later */
259 f->private_data = (void *)v;
260
261 /* Yes, we're open */
262 #ifndef LINUX_26
263 MOD_INC_USE_COUNT;
264 #endif
265 #ifndef LINUX_26_30
266 unlock_kernel();
267 #endif
268 return 0;
269 }
270
271
272 /*
273 * Driver release() function
274 */
275
276 static int sheep_net_release(struct inode *inode, struct file *f)
277 {
278 struct SheepVars *v = (struct SheepVars *)f->private_data;
279 struct sk_buff *skb;
280 D(bug("sheep_net: close\n"));
281
282 /* Detach from Ethernet card */
283 if (v->ether) {
284 dev_remove_pack(&v->pt);
285 sk_free(v->skt);
286 v->skt = NULL;
287 #ifdef LINUX_24
288 dev_put( v->ether );
289 #endif
290 v->ether = NULL;
291 }
292
293 /* Empty packet queue */
294 while ((skb = skb_dequeue(&v->queue)) != NULL)
295 dev_kfree_skb(skb);
296
297 /* Free private variables */
298 kfree(v);
299
300 /* Sorry, we're closed */
301 #ifndef LINUX_26
302 MOD_DEC_USE_COUNT;
303 #endif
304 return 0;
305 }
306
307
308 /*
309 * Check whether an Ethernet address is the local (attached) one or
310 * the fake one
311 */
312
313 static inline int is_local_addr(struct SheepVars *v, void *a)
314 {
315 return memcmp(a, v->eth_addr, 6) == 0;
316 }
317
318 static inline int is_fake_addr(struct SheepVars *v, void *a)
319 {
320 return memcmp(a, v->fake_addr, 6) == 0;
321 }
322
323
324 /*
325 * Outgoing packet. Replace the fake enet addr with the real local one.
326 */
327
328 static inline void do_demasq(struct SheepVars *v, u8 *p)
329 {
330 memcpy(p, v->eth_addr, 6);
331 }
332
333 static void demasquerade(struct SheepVars *v, struct sk_buff *skb)
334 {
335 u8 *p = skb_mac_header(skb);
336 int proto = (p[12] << 8) | p[13];
337
338 do_demasq(v, p + 6); /* source address */
339
340 /* Need to fix ARP packets */
341 if (proto == ETH_P_ARP) {
342 if (is_fake_addr(v, p + 14 + 8)) /* sender HW-addr */
343 do_demasq(v, p + 14 + 8);
344 }
345
346 /* ...and AARPs (snap code: 0x00,0x00,0x00,0x80,0xF3) */
347 if (p[17] == 0 && p[18] == 0 && p[19] == 0 && p[20] == 0x80 && p[21] == 0xf3) {
348 /* XXX: we should perhaps look for the 802 frame too */
349 if (is_fake_addr(v, p + 30))
350 do_demasq(v, p + 30); /* sender HW-addr */
351 }
352 }
353
354
355 /*
356 * Incoming packet. Replace the local enet addr with the fake one.
357 */
358
359 static inline void do_masq(struct SheepVars *v, u8 *p)
360 {
361 memcpy(p, v->fake_addr, 6);
362 }
363
364 static void masquerade(struct SheepVars *v, struct sk_buff *skb)
365 {
366 u8 *p = skb_mac_header(skb);
367 if (!(p[0] & ETH_ADDR_MULTICAST))
368 do_masq(v, p); /* destination address */
369
370 /* XXX: reverse ARP might need to be fixed */
371 }
372
373
374 /*
375 * Driver read() function
376 */
377
378 static ssize_t sheep_net_read(struct file *f, char *buf, size_t count, loff_t *off)
379 {
380 struct SheepVars *v = (struct SheepVars *)f->private_data;
381 struct sk_buff *skb;
382
383 D(bug("sheep_net: read\n"));
384
385 for (;;) {
386
387 /* Get next packet from queue */
388 skb = skb_dequeue(&v->queue);
389 if (skb != NULL || (f->f_flags & O_NONBLOCK))
390 break;
391
392 /* No packet in queue and in blocking mode, so block */
393 interruptible_sleep_on(&v->wait);
394
395 /* Signal received? Then bail out */
396 if (signal_pending(current))
397 return -EINTR;
398 }
399 if (skb == NULL)
400 return -EAGAIN;
401
402 /* Pass packet to caller */
403 if (count > skb->len)
404 count = skb->len;
405 if (copy_to_user(buf, skb->data, count))
406 count = -EFAULT;
407 dev_kfree_skb(skb);
408 return count;
409 }
410
411
412 /*
413 * Driver write() function
414 */
415
416 static ssize_t sheep_net_write(struct file *f, const char *buf, size_t count, loff_t *off)
417 {
418 struct SheepVars *v = (struct SheepVars *)f->private_data;
419 struct sk_buff *skb;
420 char *p;
421 D(bug("sheep_net: write\n"));
422
423 /* Check packet size */
424 if (count < sizeof(struct ethhdr))
425 return -EINVAL;
426 if (count > 1514) {
427 printk("sheep_net_write: packet size %ld > 1514\n", count);
428 count = 1514;
429 }
430
431 /* Interface active? */
432 if (v->ether == NULL)
433 return count;
434
435 /* Allocate buffer for packet */
436 skb = dev_alloc_skb(count);
437 if (skb == NULL)
438 return -ENOBUFS;
439
440 /* Stuff packet in buffer */
441 p = skb_put(skb, count);
442 if (copy_from_user(p, buf, count)) {
443 kfree_skb(skb);
444 return -EFAULT;
445 }
446
447 /* Transmit packet */
448 atomic_add(skb->truesize, &v->skt->wmem_alloc);
449 skb->sk = v->skt;
450 skb->dev = v->ether;
451 skb->priority = 0;
452 #if LINUX_VERSION_CODE < KERNEL_VERSION(2,6,9)
453 skb->nh.raw = skb->h.raw = skb->data + v->ether->hard_header_len;
454 skb->mac.raw = skb->data;
455 #else
456 skb_reset_mac_header(skb);
457 skb_set_transport_header(skb, v->ether->hard_header_len);
458 skb_set_network_header(skb, v->ether->hard_header_len);
459 #endif
460
461 /* Base the IP-filtering on the IP address in any outgoing ARP packets */
462 if (eth_hdr(skb)->h_proto == htons(ETH_P_ARP)) {
463 u8 *p = &skb->data[14+14]; /* source IP address */
464 u32 ip = (p[0] << 24) | (p[1] << 16) | (p[2] << 8) | p[3];
465 if (ip != v->ipfilter) {
466 v->ipfilter = ip;
467 printk("sheep_net: ipfilter set to %d.%d.%d.%d\n", (ip >> 24) & 0xff, (ip >> 16) & 0xff, (ip >> 8) & 0xff, ip & 0xff);
468 }
469 }
470
471 /* Is this packet addressed solely to the local host? */
472 if (is_local_addr(v, skb->data) && !(skb->data[0] & ETH_ADDR_MULTICAST)) {
473 skb->protocol = eth_type_trans(skb, v->ether);
474 netif_rx(skb);
475 return count;
476 }
477 if (skb->data[0] & ETH_ADDR_MULTICAST) {
478 /* We can't clone the skb since we will manipulate the data below */
479 struct sk_buff *lskb = skb_copy(skb, GFP_ATOMIC);
480 if (lskb) {
481 lskb->protocol = eth_type_trans(lskb, v->ether);
482 netif_rx(lskb);
483 }
484 }
485
486 /* Outgoing packet (will be on the net) */
487 demasquerade(v, skb);
488
489 skb->protocol = PROT_MAGIC; /* Magic value (we can recognize the packet in sheep_net_receiver) */
490 dev_queue_xmit(skb);
491 return count;
492 }
493
494
495 /*
496 * Driver poll() function
497 */
498
499 static unsigned int sheep_net_poll(struct file *f, struct poll_table_struct *wait)
500 {
501 struct SheepVars *v = (struct SheepVars *)f->private_data;
502 D(bug("sheep_net: poll\n"));
503
504 /* Packets in queue? Then return */
505 if (!skb_queue_empty(&v->queue))
506 return POLLIN | POLLRDNORM;
507
508 /* Otherwise wait for packet */
509 poll_wait(f, &v->wait, wait);
510 if (!skb_queue_empty(&v->queue))
511 return POLLIN | POLLRDNORM;
512 else
513 return 0;
514 }
515
516
517 /*
518 * Driver ioctl() function
519 */
520
521 #ifdef LINUX_26_36
522 static long sheep_net_ioctl(struct file *f, unsigned int code, unsigned long arg)
523 #else
524 static int sheep_net_ioctl(struct inode *inode, struct file *f, unsigned int code, unsigned long arg)
525 #endif
526 {
527 struct SheepVars *v = (struct SheepVars *)f->private_data;
528 D(bug("sheep_net: ioctl %04x\n", code));
529
530 switch (code) {
531
532 /* Attach to Ethernet card
533 arg: pointer to name of Ethernet device (char[20]) */
534 case SIOCSIFLINK: {
535 char name[20];
536 int err;
537
538 /* Already attached? */
539 if (v->ether)
540 return -EBUSY;
541
542 /* Get Ethernet card name */
543 if (copy_from_user(name, (void *)arg, 20))
544 return -EFAULT;
545 name[19] = 0;
546
547 /* Find card */
548 #ifdef LINUX_26
549 v->ether = dev_get_by_name(&init_net, name);
550 #elif defined(LINUX_24)
551 v->ether = dev_get_by_name(name);
552 #else
553 dev_lock_list();
554 v->ether = dev_get(name);
555 #endif
556 if (v->ether == NULL) {
557 err = -ENODEV;
558 goto error;
559 }
560
561 /* Is it Ethernet? */
562 if (v->ether->type != ARPHRD_ETHER) {
563 err = -EINVAL;
564 goto error;
565 }
566
567 /* Remember the card's hardware address */
568 memcpy(v->eth_addr, v->ether->dev_addr, 6);
569
570 /* Allocate socket */
571 #ifdef LINUX_26
572 v->skt = sk_alloc(dev_net(v->ether), GFP_USER, 1, &sheep_proto);
573 #else
574 v->skt = sk_alloc(0, GFP_USER, 1);
575 #endif
576 if (v->skt == NULL) {
577 err = -ENOMEM;
578 goto error;
579 }
580 skt_set_dead(v->skt);
581
582 /* Attach packet handler */
583 v->pt.type = htons(ETH_P_ALL);
584 v->pt.dev = v->ether;
585 v->pt.func = sheep_net_receiver;
586 dev_add_pack(&v->pt);
587 #ifndef LINUX_24
588 dev_unlock_list();
589 #endif
590 return 0;
591
592 error:
593 #ifdef LINUX_24
594 if (v->ether)
595 dev_put(v->ether);
596 #else
597 dev_unlock_list();
598 #endif
599 v->ether = NULL;
600 return err;
601 }
602
603 /* Get hardware address of the sheep_net module
604 arg: pointer to buffer (6 bytes) to store address */
605 case SIOCGIFADDR:
606 if (copy_to_user((void *)arg, v->fake_addr, 6))
607 return -EFAULT;
608 return 0;
609
610 /* Set the hardware address of the sheep_net module
611 arg: pointer to new address (6 bytes) */
612 case SIOCSIFADDR:
613 if (copy_from_user(v->fake_addr, (void*)arg, 6))
614 return -EFAULT;
615 return 0;
616
617 /* Add multicast address
618 arg: pointer to address (6 bytes) */
619 case SIOCADDMULTI: {
620 char addr[6];
621 if (v->ether == NULL)
622 return -ENODEV;
623 if (copy_from_user(addr, (void *)arg, 6))
624 return -EFAULT;
625 #ifdef LINUX_26_35
626 return dev_mc_add(v->ether, addr);
627 #else
628 return dev_mc_add(v->ether, addr, 6, 0);
629 #endif
630 }
631
632 /* Remove multicast address
633 arg: pointer to address (6 bytes) */
634 case SIOCDELMULTI: {
635 char addr[6];
636 if (v->ether == NULL)
637 return -ENODEV;
638 if (copy_from_user(addr, (void *)arg, 6))
639 return -EFAULT;
640 #ifdef LINUX_26_35
641 return dev_mc_del(v->ether, addr);
642 #else
643 return dev_mc_delete(v->ether, addr, 6, 0);
644 #endif
645 }
646
647 /* Return size of first packet in queue */
648 case FIONREAD: {
649 int count = 0;
650 struct sk_buff *skb;
651 #ifdef LINUX_24
652 unsigned long flags;
653 spin_lock_irqsave(&v->queue.lock, flags);
654 #else
655 cli();
656 #endif
657 skb = skb_peek(&v->queue);
658 if (skb)
659 count = skb->len;
660 #ifdef LINUX_24
661 spin_unlock_irqrestore(&v->queue.lock, flags);
662 #else
663 sti();
664 #endif
665 return put_user(count, (int *)arg);
666 }
667
668 case SIOC_MOL_GET_IPFILTER:
669 return put_user(v->ipfilter, (int *)arg);
670
671 case SIOC_MOL_SET_IPFILTER:
672 v->ipfilter = arg;
673 return 0;
674
675 default:
676 return -ENOIOCTLCMD;
677 }
678 }
679
680
681 /*
682 * Packet receiver function
683 */
684
685 #ifdef LINUX_26
686 static int sheep_net_receiver(struct sk_buff *skb, struct net_device *dev, struct packet_type *pt, struct net_device *foo)
687 #else
688 static int sheep_net_receiver(struct sk_buff *skb, struct net_device *dev, struct packet_type *pt)
689 #endif
690 {
691 struct SheepVars *v = (struct SheepVars *)pt;
692 struct sk_buff *skb2;
693 int fake;
694 int multicast;
695 D(bug("sheep_net: packet received\n"));
696
697 multicast = (eth_hdr(skb)->h_dest[0] & ETH_ADDR_MULTICAST);
698 fake = is_fake_addr(v, &eth_hdr(skb)->h_dest);
699
700 /* Packet sent by us? Then discard */
701 if (is_fake_addr(v, &eth_hdr(skb)->h_source) || skb->protocol == PROT_MAGIC)
702 goto drop;
703
704 /* If the packet is not meant for this host, discard it */
705 if (!is_local_addr(v, &eth_hdr(skb)->h_dest) && !multicast && !fake)
706 goto drop;
707
708 /* Discard packets if queue gets too full */
709 if (skb_queue_len(&v->queue) > MAX_QUEUE)
710 goto drop;
711
712 /* Apply any filters here (if fake is true, then we *know* we want this packet) */
713 if (!fake) {
714 if ((skb->protocol == htons(ETH_P_IP))
715 && (!v->ipfilter || (ntohl(ipip_hdr(skb)->daddr) != v->ipfilter && !multicast)))
716 goto drop;
717 }
718
719 /* Masquerade (we are typically a clone - best to make a real copy) */
720 skb2 = skb_copy(skb, GFP_ATOMIC);
721 if (!skb2)
722 goto drop;
723 kfree_skb(skb);
724 skb = skb2;
725 masquerade(v, skb);
726
727 /* We also want the Ethernet header */
728 skb_push(skb, skb->data - skb_mac_header(skb));
729
730 /* Enqueue packet */
731 skb_queue_tail(&v->queue, skb);
732
733 /* Unblock blocked read */
734 wake_up(&v->wait);
735 return 0;
736
737 drop:
738 kfree_skb(skb);
739 return 0;
740 }
741
742 MODULE_LICENSE("GPL");