Merge branch 'merge'
[pandora-kernel.git] / drivers / net / atari_bionet.c
1 /* bionet.c     BioNet-100 device driver for linux68k.
2  *
3  * Version:     @(#)bionet.c    1.0     02/06/96
4  *
5  * Author:      Hartmut Laue <laue@ifk-mp.uni-kiel.de>
6  * and          Torsten Narjes <narjes@ifk-mp.uni-kiel.de>
7  *
8  * Little adaptions for integration into pl7 by Roman Hodek
9  *
10  * Some changes in bionet_poll_rx by Karl-Heinz Lohner
11  *
12         What is it ?
13         ------------
14         This driver controls the BIONET-100 LAN-Adapter which connects
15         an ATARI ST/TT via the ACSI-port to an Ethernet-based network.
16
17         This version can be compiled as a loadable module (See the
18         compile command at the bottom of this file).
19         At load time, you can optionally set the debugging level and the
20         fastest response time on the command line of 'insmod'.
21
22         'bionet_debug'
23                 controls the amount of diagnostic messages:
24           0  : no messages
25           >0 : see code for meaning of printed messages
26
27         'bionet_min_poll_time' (always >=1)
28                 gives the time (in jiffies) between polls. Low values
29                 increase the system load (beware!)
30
31         When loaded, a net device with the name 'bio0' becomes available,
32         which can be controlled with the usual 'ifconfig' command.
33
34         It is possible to compile this driver into the kernel like other
35         (net) drivers. For this purpose, some source files (e.g. config-files
36         makefiles, Space.c) must be changed accordingly. (You may refer to
37         other drivers how to do it.) In this case, the device will be detected
38         at boot time and (probably) appear as 'eth0'.
39
40         This code is based on several sources:
41         - The driver code for a parallel port ethernet adapter by
42           Donald Becker (see file 'atp.c' from the PC linux distribution)
43         - The ACSI code by Roman Hodek for the ATARI-ACSI harddisk support
44           and DMA handling.
45         - Very limited information about moving packets in and out of the
46           BIONET-adapter from the TCP package for TOS by BioData GmbH.
47
48         Theory of Operation
49         -------------------
50         Because the ATARI DMA port is usually shared between several
51         devices (eg. harddisk, floppy) we cannot block the ACSI bus
52         while waiting for interrupts. Therefore we use a polling mechanism
53         to fetch packets from the adapter. For the same reason, we send
54         packets without checking that the previous packet has been sent to
55         the LAN. We rely on the higher levels of the networking code to detect
56         missing packets and resend them.
57
58         Before we access the ATARI DMA controller, we check if another
59         process is using the DMA. If not, we lock the DMA, perform one or
60         more packet transfers and unlock the DMA before returning.
61         We do not use 'stdma_lock' unconditionally because it is unclear
62         if the networking code can be set to sleep, which will happen if
63         another (possibly slow) device is using the DMA controller.
64
65         The polling is done via timer interrupts which periodically
66         'simulate' an interrupt from the Ethernet adapter. The time (in jiffies)
67         between polls varies depending on an estimate of the net activity.
68         The allowed range is given by the variable 'bionet_min_poll_time'
69         for the lower (fastest) limit and the constant 'MAX_POLL_TIME'
70         for the higher (slowest) limit.
71
72         Whenever a packet arrives, we switch to fastest response by setting
73         the polling time to its lowest limit. If the following poll fails,
74         because no packets have arrived, we increase the time for the next
75         poll. When the net activity is low, the polling time effectively
76         stays at its maximum value, resulting in the lowest load for the
77         machine.
78  */
79
80 #define MAX_POLL_TIME   10
81
82 static char version[] =
83         "bionet.c:v1.0 06-feb-96 (c) Hartmut Laue.\n";
84
85 #include <linux/module.h>
86
87 #include <linux/errno.h>
88 #include <linux/kernel.h>
89 #include <linux/jiffies.h>
90 #include <linux/types.h>
91 #include <linux/fcntl.h>
92 #include <linux/interrupt.h>
93 #include <linux/ioport.h>
94 #include <linux/in.h>
95 #include <linux/slab.h>
96 #include <linux/string.h>
97 #include <linux/delay.h>
98 #include <linux/timer.h>
99 #include <linux/init.h>
100 #include <linux/bitops.h>
101
102 #include <linux/netdevice.h>
103 #include <linux/etherdevice.h>
104 #include <linux/skbuff.h>
105
106 #include <asm/setup.h>
107 #include <asm/pgtable.h>
108 #include <asm/system.h>
109 #include <asm/io.h>
110 #include <asm/dma.h>
111 #include <asm/atarihw.h>
112 #include <asm/atariints.h>
113 #include <asm/atari_acsi.h>
114 #include <asm/atari_stdma.h>
115
116
117 /* use 0 for production, 1 for verification, >2 for debug
118  */
119 #ifndef NET_DEBUG
120 #define NET_DEBUG 0
121 #endif
122 /*
123  * Global variable 'bionet_debug'. Can be set at load time by 'insmod'
124  */
125 unsigned int bionet_debug = NET_DEBUG;
126 module_param(bionet_debug, int, 0);
127 MODULE_PARM_DESC(bionet_debug, "bionet debug level (0-2)");
128 MODULE_LICENSE("GPL");
129
130 static unsigned int bionet_min_poll_time = 2;
131
132
133 /* Information that need to be kept for each board.
134  */
135 struct net_local {
136         struct net_device_stats stats;
137         long open_time;                 /* for debugging */
138         int  poll_time;                 /* polling time varies with net load */
139 };
140
141 static struct nic_pkt_s {               /* packet format */
142         unsigned char   status;
143         unsigned char   dummy;
144         unsigned char   l_lo, l_hi;
145         unsigned char   buffer[3000];
146 } *nic_packet;
147 unsigned char *phys_nic_packet;
148
149 /* Index to functions, as function prototypes.
150  */
151 static int bionet_open(struct net_device *dev);
152 static int bionet_send_packet(struct sk_buff *skb, struct net_device *dev);
153 static void bionet_poll_rx(struct net_device *);
154 static int bionet_close(struct net_device *dev);
155 static struct net_device_stats *net_get_stats(struct net_device *dev);
156 static void bionet_tick(unsigned long);
157
158 static DEFINE_TIMER(bionet_timer, bionet_tick, 0, 0);
159
160 #define STRAM_ADDR(a)   (((a) & 0xff000000) == 0)
161
162 /* The following routines access the ethernet board connected to the
163  * ACSI port via the st_dma chip.
164  */
165 #define NODE_ADR 0x60
166
167 #define C_READ 8
168 #define C_WRITE 0x0a
169 #define C_GETEA 0x0f
170 #define C_SETCR 0x0e
171
172 static int
173 sendcmd(unsigned int a0, unsigned int mod, unsigned int cmd) {
174         unsigned int c;
175
176         dma_wd.dma_mode_status = (mod | ((a0) ? 2 : 0) | 0x88);
177         dma_wd.fdc_acces_seccount = cmd;
178         dma_wd.dma_mode_status = (mod | 0x8a);
179
180         if( !acsi_wait_for_IRQ(HZ/2) )  /* wait for cmd ack */
181                 return -1;              /* timeout */
182
183         c = dma_wd.fdc_acces_seccount;
184         return (c & 0xff);
185 }
186
187
188 static void
189 set_status(int cr) {
190         sendcmd(0,0x100,NODE_ADR | C_SETCR);    /* CMD: SET CR */
191         sendcmd(1,0x100,cr);
192
193         dma_wd.dma_mode_status = 0x80;
194 }
195
196 static int
197 get_status(unsigned char *adr) {
198         int i,c;
199
200         DISABLE_IRQ();
201         c = sendcmd(0,0x00,NODE_ADR | C_GETEA);  /* CMD: GET ETH ADR*/
202         if( c < 0 ) goto gsend;
203
204         /* now read status bytes */
205
206         for (i=0; i<6; i++) {
207                 dma_wd.fdc_acces_seccount = 0;  /* request next byte */
208
209                 if( !acsi_wait_for_IRQ(HZ/2) ) {        /* wait for cmd ack */
210                         c = -1;
211                         goto gsend;             /* timeout */
212                 }
213                 c = dma_wd.fdc_acces_seccount;
214                 *adr++ = (unsigned char)c;
215         }
216         c = 1;
217 gsend:
218         dma_wd.dma_mode_status = 0x80;
219         return c;
220 }
221
222 static irqreturn_t
223 bionet_intr(int irq, void *data, struct pt_regs *fp) {
224         return IRQ_HANDLED;
225 }
226
227
228 static int
229 get_frame(unsigned long paddr, int odd) {
230         int c;
231         unsigned long flags;
232
233         DISABLE_IRQ();
234         local_irq_save(flags);
235
236         dma_wd.dma_mode_status          = 0x9a;
237         dma_wd.dma_mode_status          = 0x19a;
238         dma_wd.dma_mode_status          = 0x9a;
239         dma_wd.fdc_acces_seccount       = 0x04;         /* sector count (was 5) */
240         dma_wd.dma_lo                   = (unsigned char)paddr;
241         paddr >>= 8;
242         dma_wd.dma_md                   = (unsigned char)paddr;
243         paddr >>= 8;
244         dma_wd.dma_hi                   = (unsigned char)paddr;
245         local_irq_restore(flags);
246
247         c = sendcmd(0,0x00,NODE_ADR | C_READ);  /* CMD: READ */
248         if( c < 128 ) goto rend;
249
250         /* now read block */
251
252         c = sendcmd(1,0x00,odd);        /* odd flag for address shift */
253         dma_wd.dma_mode_status  = 0x0a;
254
255         if( !acsi_wait_for_IRQ(100) ) { /* wait for DMA to complete */
256                 c = -1;
257                 goto rend;
258         }
259         dma_wd.dma_mode_status  = 0x8a;
260         dma_wd.dma_mode_status  = 0x18a;
261         dma_wd.dma_mode_status  = 0x8a;
262         c = dma_wd.fdc_acces_seccount;
263
264         dma_wd.dma_mode_status  = 0x88;
265         c = dma_wd.fdc_acces_seccount;
266         c = 1;
267
268 rend:
269         dma_wd.dma_mode_status  = 0x80;
270         udelay(40);
271         acsi_wait_for_noIRQ(20);
272         return c;
273 }
274
275
276 static int
277 hardware_send_packet(unsigned long paddr, int cnt) {
278         unsigned int c;
279         unsigned long flags;
280
281         DISABLE_IRQ();
282         local_irq_save(flags);
283
284         dma_wd.dma_mode_status  = 0x19a;
285         dma_wd.dma_mode_status  = 0x9a;
286         dma_wd.dma_mode_status  = 0x19a;
287         dma_wd.dma_lo           = (unsigned char)paddr;
288         paddr >>= 8;
289         dma_wd.dma_md           = (unsigned char)paddr;
290         paddr >>= 8;
291         dma_wd.dma_hi           = (unsigned char)paddr;
292
293         dma_wd.fdc_acces_seccount       = 0x4;          /* sector count */
294         local_irq_restore(flags);
295
296         c = sendcmd(0,0x100,NODE_ADR | C_WRITE);        /* CMD: WRITE */
297         c = sendcmd(1,0x100,cnt&0xff);
298         c = sendcmd(1,0x100,cnt>>8);
299
300         /* now write block */
301
302         dma_wd.dma_mode_status  = 0x10a;        /* DMA enable */
303         if( !acsi_wait_for_IRQ(100) )           /* wait for DMA to complete */
304                 goto end;
305
306         dma_wd.dma_mode_status  = 0x19a;        /* DMA disable ! */
307         c = dma_wd.fdc_acces_seccount;
308
309 end:
310         c = sendcmd(1,0x100,0);
311         c = sendcmd(1,0x100,0);
312
313         dma_wd.dma_mode_status  = 0x180;
314         udelay(40);
315         acsi_wait_for_noIRQ(20);
316         return( c & 0x02);
317 }
318
319
320 /* Check for a network adaptor of this type, and return '0' if one exists.
321  */
322 struct net_device * __init bionet_probe(int unit)
323 {
324         struct net_device *dev;
325         unsigned char station_addr[6];
326         static unsigned version_printed;
327         static int no_more_found;       /* avoid "Probing for..." printed 4 times */
328         int i;
329         int err;
330
331         if (!MACH_IS_ATARI || no_more_found)
332                 return ERR_PTR(-ENODEV);
333
334         dev = alloc_etherdev(sizeof(struct net_local));
335         if (!dev)
336                 return ERR_PTR(-ENOMEM);
337         if (unit >= 0) {
338                 sprintf(dev->name, "eth%d", unit);
339                 netdev_boot_setup_check(dev);
340         }
341         SET_MODULE_OWNER(dev);
342
343         printk("Probing for BioNet 100 Adapter...\n");
344
345         stdma_lock(bionet_intr, NULL);
346         i = get_status(station_addr);   /* Read the station address PROM.  */
347         ENABLE_IRQ();
348         stdma_release();
349
350         /* Check the first three octets of the S.A. for the manufactor's code.
351          */
352
353         if( i < 0
354         ||  station_addr[0] != 'B'
355         ||  station_addr[1] != 'I'
356         ||  station_addr[2] != 'O' ) {
357                 no_more_found = 1;
358                 printk( "No BioNet 100 found.\n" );
359                 free_netdev(dev);
360                 return ERR_PTR(-ENODEV);
361         }
362
363         if (bionet_debug > 0 && version_printed++ == 0)
364                 printk(version);
365
366         printk("%s: %s found, eth-addr: %02x-%02x-%02x:%02x-%02x-%02x.\n",
367                 dev->name, "BioNet 100",
368                 station_addr[0], station_addr[1], station_addr[2],
369                 station_addr[3], station_addr[4], station_addr[5]);
370
371         /* Initialize the device structure. */
372
373         nic_packet = (struct nic_pkt_s *)acsi_buffer;
374         phys_nic_packet = (unsigned char *)phys_acsi_buffer;
375         if (bionet_debug > 0) {
376                 printk("nic_packet at 0x%p, phys at 0x%p\n",
377                         nic_packet, phys_nic_packet );
378         }
379
380         dev->open               = bionet_open;
381         dev->stop               = bionet_close;
382         dev->hard_start_xmit    = bionet_send_packet;
383         dev->get_stats          = net_get_stats;
384
385         /* Fill in the fields of the device structure with ethernet-generic
386          * values. This should be in a common file instead of per-driver.
387          */
388
389         for (i = 0; i < ETH_ALEN; i++) {
390 #if 0
391                 dev->broadcast[i] = 0xff;
392 #endif
393                 dev->dev_addr[i]  = station_addr[i];
394         }
395         err = register_netdev(dev);
396         if (!err)
397                 return dev;
398         free_netdev(dev);
399         return ERR_PTR(err);
400 }
401
402 /* Open/initialize the board.  This is called (in the current kernel)
403    sometime after booting when the 'ifconfig' program is run.
404
405    This routine should set everything up anew at each open, even
406    registers that "should" only need to be set once at boot, so that
407    there is non-reboot way to recover if something goes wrong.
408  */
409 static int
410 bionet_open(struct net_device *dev) {
411         struct net_local *lp = netdev_priv(dev);
412
413         if (bionet_debug > 0)
414                 printk("bionet_open\n");
415         stdma_lock(bionet_intr, NULL);
416
417         /* Reset the hardware here.
418          */
419         set_status(4);
420         lp->open_time = 0;      /*jiffies*/
421         lp->poll_time = MAX_POLL_TIME;
422
423         dev->tbusy = 0;
424         dev->interrupt = 0;
425         dev->start = 1;
426
427         stdma_release();
428         bionet_timer.data = (long)dev;
429         bionet_timer.expires = jiffies + lp->poll_time;
430         add_timer(&bionet_timer);
431         return 0;
432 }
433
434 static int
435 bionet_send_packet(struct sk_buff *skb, struct net_device *dev) {
436         struct net_local *lp = netdev_priv(dev);
437         unsigned long flags;
438
439         /* Block a timer-based transmit from overlapping.  This could better be
440          * done with atomic_swap(1, dev->tbusy), but set_bit() works as well.
441          */
442         local_irq_save(flags);
443
444         if (stdma_islocked()) {
445                 local_irq_restore(flags);
446                 lp->stats.tx_errors++;
447         }
448         else {
449                 int length = ETH_ZLEN < skb->len ? skb->len : ETH_ZLEN;
450                 unsigned long buf = virt_to_phys(skb->data);
451                 int stat;
452
453                 stdma_lock(bionet_intr, NULL);
454                 local_irq_restore(flags);
455                 if( !STRAM_ADDR(buf+length-1) ) {
456                         memcpy(nic_packet->buffer, skb->data, length);
457                         buf = (unsigned long)&((struct nic_pkt_s *)phys_nic_packet)->buffer;
458                 }
459
460                 if (bionet_debug >1) {
461                         u_char *data = nic_packet->buffer, *p;
462                         int i;
463                         
464                         printk( "%s: TX pkt type 0x%4x from ", dev->name,
465                                   ((u_short *)data)[6]);
466
467                         for( p = &data[6], i = 0; i < 6; i++ )
468                                 printk("%02x%s", *p++,i != 5 ? ":" : "" );
469                         printk(" to ");
470
471                         for( p = data, i = 0; i < 6; i++ )
472                                 printk("%02x%s", *p++,i != 5 ? ":" : "" "\n" );
473
474                         printk( "%s: ", dev->name );
475                         printk(" data %02x%02x %02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x"
476                                " %02x%02x%02x%02x len %d\n",
477                                   data[12], data[13], data[14], data[15], data[16], data[17], data[18], data[19],
478                                   data[20], data[21], data[22], data[23], data[24], data[25], data[26], data[27],
479                                   data[28], data[29], data[30], data[31], data[32], data[33],
480                                   length );
481                 }
482                 dma_cache_maintenance(buf, length, 1);
483
484                 stat = hardware_send_packet(buf, length);
485                 ENABLE_IRQ();
486                 stdma_release();
487
488                 dev->trans_start = jiffies;
489                 dev->tbusy       = 0;
490                 lp->stats.tx_packets++;
491                 lp->stats.tx_bytes+=length;
492         }
493         dev_kfree_skb(skb);
494
495         return 0;
496 }
497
498 /* We have a good packet(s), get it/them out of the buffers.
499  */
500 static void
501 bionet_poll_rx(struct net_device *dev) {
502         struct net_local *lp = netdev_priv(dev);
503         int boguscount = 10;
504         int pkt_len, status;
505         unsigned long flags;
506
507         local_irq_save(flags);
508         /* ++roman: Take care at locking the ST-DMA... This must be done with ints
509          * off, since otherwise an int could slip in between the question and the
510          * locking itself, and then we'd go to sleep... And locking itself is
511          * necessary to keep the floppy_change timer from working with ST-DMA
512          * registers. */
513         if (stdma_islocked()) {
514                 local_irq_restore(flags);
515                 return;
516         }
517         stdma_lock(bionet_intr, NULL);
518         DISABLE_IRQ();
519         local_irq_restore(flags);
520
521         if( lp->poll_time < MAX_POLL_TIME ) lp->poll_time++;
522
523         while(boguscount--) {
524                 status = get_frame((unsigned long)phys_nic_packet, 0);
525
526                 if( status == 0 ) break;
527
528                 /* Good packet... */
529
530                 dma_cache_maintenance((unsigned long)phys_nic_packet, 1520, 0);
531
532                 pkt_len = (nic_packet->l_hi << 8) | nic_packet->l_lo;
533
534                 lp->poll_time = bionet_min_poll_time;    /* fast poll */
535                 if( pkt_len >= 60 && pkt_len <= 1520 ) {
536                                         /*      ^^^^ war 1514  KHL */
537                         /* Malloc up new buffer.
538                          */
539                         struct sk_buff *skb = dev_alloc_skb( pkt_len + 2 );
540                         if (skb == NULL) {
541                                 printk("%s: Memory squeeze, dropping packet.\n",
542                                         dev->name);
543                                 lp->stats.rx_dropped++;
544                                 break;
545                         }
546
547                         skb->dev = dev;
548                         skb_reserve( skb, 2 );          /* 16 Byte align  */
549                         skb_put( skb, pkt_len );        /* make room */
550
551                         /* 'skb->data' points to the start of sk_buff data area.
552                          */
553                         memcpy(skb->data, nic_packet->buffer, pkt_len);
554                         skb->protocol = eth_type_trans( skb, dev ); 
555                         netif_rx(skb);
556                         dev->last_rx = jiffies;
557                         lp->stats.rx_packets++;
558                         lp->stats.rx_bytes+=pkt_len;
559
560         /* If any worth-while packets have been received, dev_rint()
561            has done a mark_bh(INET_BH) for us and will work on them
562            when we get to the bottom-half routine.
563          */
564
565                         if (bionet_debug >1) {
566                                 u_char *data = nic_packet->buffer, *p;
567                                 int i;
568                                 
569                                 printk( "%s: RX pkt type 0x%4x from ", dev->name,
570                                           ((u_short *)data)[6]);
571                                          
572                                 
573                                 for( p = &data[6], i = 0; i < 6; i++ )
574                                         printk("%02x%s", *p++,i != 5 ? ":" : "" );
575                                 printk(" to ");
576                                 for( p = data, i = 0; i < 6; i++ )
577                                         printk("%02x%s", *p++,i != 5 ? ":" : "" "\n" );
578  
579                                 printk( "%s: ", dev->name );
580                                 printk(" data %02x%02x %02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x %02x%02x%02x%02x"
581                                        " %02x%02x%02x%02x len %d\n",
582                                           data[12], data[13], data[14], data[15], data[16], data[17], data[18], data[19],
583                                           data[20], data[21], data[22], data[23], data[24], data[25], data[26], data[27],
584                                           data[28], data[29], data[30], data[31], data[32], data[33],
585                                                   pkt_len );
586                         }
587                 }
588                 else {
589                         printk(" Packet has wrong length: %04d bytes\n", pkt_len);
590                         lp->stats.rx_errors++;
591                 }
592         }
593         stdma_release();
594         ENABLE_IRQ();
595         return;
596 }
597
598 /* bionet_tick: called by bionet_timer. Reads packets from the adapter,
599  * passes them to the higher layers and restarts the timer.
600  */
601 static void
602 bionet_tick(unsigned long data) {
603         struct net_device        *dev = (struct net_device *)data;
604         struct net_local *lp = netdev_priv(dev);
605
606         if( bionet_debug > 0 && (lp->open_time++ & 7) == 8 )
607                 printk("bionet_tick: %ld\n", lp->open_time);
608
609         if( !stdma_islocked() ) bionet_poll_rx(dev);
610
611         bionet_timer.expires = jiffies + lp->poll_time;
612         add_timer(&bionet_timer);
613 }
614
615 /* The inverse routine to bionet_open().
616  */
617 static int
618 bionet_close(struct net_device *dev) {
619         struct net_local *lp = netdev_priv(dev);
620
621         if (bionet_debug > 0)
622                 printk("bionet_close, open_time=%ld\n", lp->open_time);
623         del_timer(&bionet_timer);
624         stdma_lock(bionet_intr, NULL);
625
626         set_status(0);
627         lp->open_time = 0;
628
629         dev->tbusy = 1;
630         dev->start = 0;
631
632         stdma_release();
633         return 0;
634 }
635
636 /* Get the current statistics.
637    This may be called with the card open or closed.
638  */
639 static struct net_device_stats *net_get_stats(struct net_device *dev) 
640 {
641         struct net_local *lp = netdev_priv(dev);
642         return &lp->stats;
643 }
644
645
646 #ifdef MODULE
647
648 static struct net_device *bio_dev;
649
650 int init_module(void)
651 {
652         bio_dev = bionet_probe(-1);
653         if (IS_ERR(bio_dev))
654                 return PTR_ERR(bio_dev);
655         return 0;
656 }
657
658 void cleanup_module(void)
659 {
660         unregister_netdev(bio_dev);
661         free_netdev(bio_dev);
662 }
663
664 #endif /* MODULE */
665
666 /* Local variables:
667  *  compile-command: "gcc -D__KERNEL__ -I/usr/src/linux/include
668         -b m68k-linuxaout -Wall -Wstrict-prototypes -O2
669         -fomit-frame-pointer -pipe -DMODULE -I../../net/inet -c bionet.c"
670  *  version-control: t
671  *  kept-new-versions: 5
672  *  tab-width: 8
673  * End:
674  */