OpenCores
URL https://opencores.org/ocsvn/test_project/test_project/trunk

Subversion Repositories test_project

[/] [test_project/] [trunk/] [linux_sd_driver/] [drivers/] [net/] [wan/] [cosa.c] - Blame information for rev 62

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 62 marcus.erl
/* $Id: cosa.c,v 1.31 2000/03/08 17:47:16 kas Exp $ */
2
 
3
/*
4
 *  Copyright (C) 1995-1997  Jan "Yenya" Kasprzak <kas@fi.muni.cz>
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., 675 Mass Ave, Cambridge, MA 02139, USA.
19
 */
20
 
21
/*
22
 * The driver for the SRP and COSA synchronous serial cards.
23
 *
24
 * HARDWARE INFO
25
 *
26
 * Both cards are developed at the Institute of Computer Science,
27
 * Masaryk University (http://www.ics.muni.cz/). The hardware is
28
 * developed by Jiri Novotny <novotny@ics.muni.cz>. More information
29
 * and the photo of both cards is available at
30
 * http://www.pavoucek.cz/cosa.html. The card documentation, firmwares
31
 * and other goods can be downloaded from ftp://ftp.ics.muni.cz/pub/cosa/.
32
 * For Linux-specific utilities, see below in the "Software info" section.
33
 * If you want to order the card, contact Jiri Novotny.
34
 *
35
 * The SRP (serial port?, the Czech word "srp" means "sickle") card
36
 * is a 2-port intelligent (with its own 8-bit CPU) synchronous serial card
37
 * with V.24 interfaces up to 80kb/s each.
38
 *
39
 * The COSA (communication serial adapter?, the Czech word "kosa" means
40
 * "scythe") is a next-generation sync/async board with two interfaces
41
 * - currently any of V.24, X.21, V.35 and V.36 can be selected.
42
 * It has a 16-bit SAB80166 CPU and can do up to 10 Mb/s per channel.
43
 * The 8-channels version is in development.
44
 *
45
 * Both types have downloadable firmware and communicate via ISA DMA.
46
 * COSA can be also a bus-mastering device.
47
 *
48
 * SOFTWARE INFO
49
 *
50
 * The homepage of the Linux driver is at http://www.fi.muni.cz/~kas/cosa/.
51
 * The CVS tree of Linux driver can be viewed there, as well as the
52
 * firmware binaries and user-space utilities for downloading the firmware
53
 * into the card and setting up the card.
54
 *
55
 * The Linux driver (unlike the present *BSD drivers :-) can work even
56
 * for the COSA and SRP in one computer and allows each channel to work
57
 * in one of the three modes (character device, Cisco HDLC, Sync PPP).
58
 *
59
 * AUTHOR
60
 *
61
 * The Linux driver was written by Jan "Yenya" Kasprzak <kas@fi.muni.cz>.
62
 *
63
 * You can mail me bugfixes and even success reports. I am especially
64
 * interested in the SMP and/or muliti-channel success/failure reports
65
 * (I wonder if I did the locking properly :-).
66
 *
67
 * THE AUTHOR USED THE FOLLOWING SOURCES WHEN PROGRAMMING THE DRIVER
68
 *
69
 * The COSA/SRP NetBSD driver by Zdenek Salvet and Ivos Cernohlavek
70
 * The skeleton.c by Donald Becker
71
 * The SDL Riscom/N2 driver by Mike Natale
72
 * The Comtrol Hostess SV11 driver by Alan Cox
73
 * The Sync PPP/Cisco HDLC layer (syncppp.c) ported to Linux by Alan Cox
74
 */
75
/*
76
 *     5/25/1999 : Marcelo Tosatti <marcelo@conectiva.com.br>
77
 *             fixed a deadlock in cosa_sppp_open
78
 */
79
 
80
/* ---------- Headers, macros, data structures ---------- */
81
 
82
#include <linux/module.h>
83
#include <linux/kernel.h>
84
#include <linux/slab.h>
85
#include <linux/poll.h>
86
#include <linux/fs.h>
87
#include <linux/interrupt.h>
88
#include <linux/delay.h>
89
#include <linux/errno.h>
90
#include <linux/ioport.h>
91
#include <linux/netdevice.h>
92
#include <linux/spinlock.h>
93
#include <linux/device.h>
94
 
95
#undef COSA_SLOW_IO     /* for testing purposes only */
96
 
97
#include <asm/io.h>
98
#include <asm/dma.h>
99
#include <asm/byteorder.h>
100
 
101
#include <net/syncppp.h>
102
#include "cosa.h"
103
 
104
/* Maximum length of the identification string. */
105
#define COSA_MAX_ID_STRING      128
106
 
107
/* Maximum length of the channel name */
108
#define COSA_MAX_NAME           (sizeof("cosaXXXcXXX")+1)
109
 
110
/* Per-channel data structure */
111
 
112
struct channel_data {
113
        void *if_ptr;   /* General purpose pointer (used by SPPP) */
114
        int usage;      /* Usage count; >0 for chrdev, -1 for netdev */
115
        int num;        /* Number of the channel */
116
        struct cosa_data *cosa; /* Pointer to the per-card structure */
117
        int txsize;     /* Size of transmitted data */
118
        char *txbuf;    /* Transmit buffer */
119
        char name[COSA_MAX_NAME];       /* channel name */
120
 
121
        /* The HW layer interface */
122
        /* routine called from the RX interrupt */
123
        char *(*setup_rx)(struct channel_data *channel, int size);
124
        /* routine called when the RX is done (from the EOT interrupt) */
125
        int (*rx_done)(struct channel_data *channel);
126
        /* routine called when the TX is done (from the EOT interrupt) */
127
        int (*tx_done)(struct channel_data *channel, int size);
128
 
129
        /* Character device parts */
130
        struct semaphore rsem, wsem;
131
        char *rxdata;
132
        int rxsize;
133
        wait_queue_head_t txwaitq, rxwaitq;
134
        int tx_status, rx_status;
135
 
136
        /* SPPP/HDLC device parts */
137
        struct ppp_device pppdev;
138
        struct sk_buff *rx_skb, *tx_skb;
139
        struct net_device_stats stats;
140
};
141
 
142
/* cosa->firmware_status bits */
143
#define COSA_FW_RESET           (1<<0)  /* Is the ROM monitor active? */
144
#define COSA_FW_DOWNLOAD        (1<<1)  /* Is the microcode downloaded? */
145
#define COSA_FW_START           (1<<2)  /* Is the microcode running? */
146
 
147
struct cosa_data {
148
        int num;                        /* Card number */
149
        char name[COSA_MAX_NAME];       /* Card name - e.g "cosa0" */
150
        unsigned int datareg, statusreg;        /* I/O ports */
151
        unsigned short irq, dma;        /* IRQ and DMA number */
152
        unsigned short startaddr;       /* Firmware start address */
153
        unsigned short busmaster;       /* Use busmastering? */
154
        int nchannels;                  /* # of channels on this card */
155
        int driver_status;              /* For communicating with firmware */
156
        int firmware_status;            /* Downloaded, reseted, etc. */
157
        unsigned long rxbitmap, txbitmap;/* Bitmap of channels who are willing to send/receive data */
158
        unsigned long rxtx;             /* RX or TX in progress? */
159
        int enabled;
160
        int usage;                              /* usage count */
161
        int txchan, txsize, rxsize;
162
        struct channel_data *rxchan;
163
        char *bouncebuf;
164
        char *txbuf, *rxbuf;
165
        struct channel_data *chan;
166
        spinlock_t lock;        /* For exclusive operations on this structure */
167
        char id_string[COSA_MAX_ID_STRING];     /* ROM monitor ID string */
168
        char *type;                             /* card type */
169
};
170
 
171
/*
172
 * Define this if you want all the possible ports to be autoprobed.
173
 * It is here but it probably is not a good idea to use this.
174
 */
175
/* #define COSA_ISA_AUTOPROBE   1 */
176
 
177
/*
178
 * Character device major number. 117 was allocated for us.
179
 * The value of 0 means to allocate a first free one.
180
 */
181
static int cosa_major = 117;
182
 
183
/*
184
 * Encoding of the minor numbers:
185
 * The lowest CARD_MINOR_BITS bits means the channel on the single card,
186
 * the highest bits means the card number.
187
 */
188
#define CARD_MINOR_BITS 4       /* How many bits in minor number are reserved
189
                                 * for the single card */
190
/*
191
 * The following depends on CARD_MINOR_BITS. Unfortunately, the "MODULE_STRING"
192
 * macro doesn't like anything other than the raw number as an argument :-(
193
 */
194
#define MAX_CARDS       16
195
/* #define MAX_CARDS    (1 << (8-CARD_MINOR_BITS)) */
196
 
197
#define DRIVER_RX_READY         0x0001
198
#define DRIVER_TX_READY         0x0002
199
#define DRIVER_TXMAP_SHIFT      2
200
#define DRIVER_TXMAP_MASK       0x0c    /* FIXME: 0xfc for 8-channel version */
201
 
202
/*
203
 * for cosa->rxtx - indicates whether either transmit or receive is
204
 * in progress. These values are mean number of the bit.
205
 */
206
#define TXBIT 0
207
#define RXBIT 1
208
#define IRQBIT 2
209
 
210
#define COSA_MTU 2000   /* FIXME: I don't know this exactly */
211
 
212
#undef DEBUG_DATA //1   /* Dump the data read or written to the channel */
213
#undef DEBUG_IRQS //1   /* Print the message when the IRQ is received */
214
#undef DEBUG_IO   //1   /* Dump the I/O traffic */
215
 
216
#define TX_TIMEOUT      (5*HZ)
217
 
218
/* Maybe the following should be allocated dynamically */
219
static struct cosa_data cosa_cards[MAX_CARDS];
220
static int nr_cards;
221
 
222
#ifdef COSA_ISA_AUTOPROBE
223
static int io[MAX_CARDS+1]  = { 0x220, 0x228, 0x210, 0x218, 0, };
224
/* NOTE: DMA is not autoprobed!!! */
225
static int dma[MAX_CARDS+1] = { 1, 7, 1, 7, 1, 7, 1, 7, 0, };
226
#else
227
static int io[MAX_CARDS+1];
228
static int dma[MAX_CARDS+1];
229
#endif
230
/* IRQ can be safely autoprobed */
231
static int irq[MAX_CARDS+1] = { -1, -1, -1, -1, -1, -1, 0, };
232
 
233
/* for class stuff*/
234
static struct class *cosa_class;
235
 
236
#ifdef MODULE
237
module_param_array(io, int, NULL, 0);
238
MODULE_PARM_DESC(io, "The I/O bases of the COSA or SRP cards");
239
module_param_array(irq, int, NULL, 0);
240
MODULE_PARM_DESC(irq, "The IRQ lines of the COSA or SRP cards");
241
module_param_array(dma, int, NULL, 0);
242
MODULE_PARM_DESC(dma, "The DMA channels of the COSA or SRP cards");
243
 
244
MODULE_AUTHOR("Jan \"Yenya\" Kasprzak, <kas@fi.muni.cz>");
245
MODULE_DESCRIPTION("Modular driver for the COSA or SRP synchronous card");
246
MODULE_LICENSE("GPL");
247
#endif
248
 
249
/* I use this mainly for testing purposes */
250
#ifdef COSA_SLOW_IO
251
#define cosa_outb outb_p
252
#define cosa_outw outw_p
253
#define cosa_inb  inb_p
254
#define cosa_inw  inw_p
255
#else
256
#define cosa_outb outb
257
#define cosa_outw outw
258
#define cosa_inb  inb
259
#define cosa_inw  inw
260
#endif
261
 
262
#define is_8bit(cosa)           (!(cosa->datareg & 0x08))
263
 
264
#define cosa_getstatus(cosa)    (cosa_inb(cosa->statusreg))
265
#define cosa_putstatus(cosa, stat)      (cosa_outb(stat, cosa->statusreg))
266
#define cosa_getdata16(cosa)    (cosa_inw(cosa->datareg))
267
#define cosa_getdata8(cosa)     (cosa_inb(cosa->datareg))
268
#define cosa_putdata16(cosa, dt)        (cosa_outw(dt, cosa->datareg))
269
#define cosa_putdata8(cosa, dt) (cosa_outb(dt, cosa->datareg))
270
 
271
/* Initialization stuff */
272
static int cosa_probe(int ioaddr, int irq, int dma);
273
 
274
/* HW interface */
275
static void cosa_enable_rx(struct channel_data *chan);
276
static void cosa_disable_rx(struct channel_data *chan);
277
static int cosa_start_tx(struct channel_data *channel, char *buf, int size);
278
static void cosa_kick(struct cosa_data *cosa);
279
static int cosa_dma_able(struct channel_data *chan, char *buf, int data);
280
 
281
/* SPPP/HDLC stuff */
282
static void sppp_channel_init(struct channel_data *chan);
283
static void sppp_channel_delete(struct channel_data *chan);
284
static int cosa_sppp_open(struct net_device *d);
285
static int cosa_sppp_close(struct net_device *d);
286
static void cosa_sppp_timeout(struct net_device *d);
287
static int cosa_sppp_tx(struct sk_buff *skb, struct net_device *d);
288
static char *sppp_setup_rx(struct channel_data *channel, int size);
289
static int sppp_rx_done(struct channel_data *channel);
290
static int sppp_tx_done(struct channel_data *channel, int size);
291
static int cosa_sppp_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd);
292
static struct net_device_stats *cosa_net_stats(struct net_device *dev);
293
 
294
/* Character device */
295
static void chardev_channel_init(struct channel_data *chan);
296
static char *chrdev_setup_rx(struct channel_data *channel, int size);
297
static int chrdev_rx_done(struct channel_data *channel);
298
static int chrdev_tx_done(struct channel_data *channel, int size);
299
static ssize_t cosa_read(struct file *file,
300
        char __user *buf, size_t count, loff_t *ppos);
301
static ssize_t cosa_write(struct file *file,
302
        const char __user *buf, size_t count, loff_t *ppos);
303
static unsigned int cosa_poll(struct file *file, poll_table *poll);
304
static int cosa_open(struct inode *inode, struct file *file);
305
static int cosa_release(struct inode *inode, struct file *file);
306
static int cosa_chardev_ioctl(struct inode *inode, struct file *file,
307
        unsigned int cmd, unsigned long arg);
308
#ifdef COSA_FASYNC_WORKING
309
static int cosa_fasync(struct inode *inode, struct file *file, int on);
310
#endif
311
 
312
static const struct file_operations cosa_fops = {
313
        .owner          = THIS_MODULE,
314
        .llseek         = no_llseek,
315
        .read           = cosa_read,
316
        .write          = cosa_write,
317
        .poll           = cosa_poll,
318
        .ioctl          = cosa_chardev_ioctl,
319
        .open           = cosa_open,
320
        .release        = cosa_release,
321
#ifdef COSA_FASYNC_WORKING
322
        .fasync         = cosa_fasync,
323
#endif
324
};
325
 
326
/* Ioctls */
327
static int cosa_start(struct cosa_data *cosa, int address);
328
static int cosa_reset(struct cosa_data *cosa);
329
static int cosa_download(struct cosa_data *cosa, void __user *a);
330
static int cosa_readmem(struct cosa_data *cosa, void __user *a);
331
 
332
/* COSA/SRP ROM monitor */
333
static int download(struct cosa_data *cosa, const char __user *data, int addr, int len);
334
static int startmicrocode(struct cosa_data *cosa, int address);
335
static int readmem(struct cosa_data *cosa, char __user *data, int addr, int len);
336
static int cosa_reset_and_read_id(struct cosa_data *cosa, char *id);
337
 
338
/* Auxilliary functions */
339
static int get_wait_data(struct cosa_data *cosa);
340
static int put_wait_data(struct cosa_data *cosa, int data);
341
static int puthexnumber(struct cosa_data *cosa, int number);
342
static void put_driver_status(struct cosa_data *cosa);
343
static void put_driver_status_nolock(struct cosa_data *cosa);
344
 
345
/* Interrupt handling */
346
static irqreturn_t cosa_interrupt(int irq, void *cosa);
347
 
348
/* I/O ops debugging */
349
#ifdef DEBUG_IO
350
static void debug_data_in(struct cosa_data *cosa, int data);
351
static void debug_data_out(struct cosa_data *cosa, int data);
352
static void debug_data_cmd(struct cosa_data *cosa, int data);
353
static void debug_status_in(struct cosa_data *cosa, int status);
354
static void debug_status_out(struct cosa_data *cosa, int status);
355
#endif
356
 
357
 
358
/* ---------- Initialization stuff ---------- */
359
 
360
static int __init cosa_init(void)
361
{
362
        int i, err = 0;
363
 
364
        printk(KERN_INFO "cosa v1.08 (c) 1997-2000 Jan Kasprzak <kas@fi.muni.cz>\n");
365
#ifdef CONFIG_SMP
366
        printk(KERN_INFO "cosa: SMP found. Please mail any success/failure reports to the author.\n");
367
#endif
368
        if (cosa_major > 0) {
369
                if (register_chrdev(cosa_major, "cosa", &cosa_fops)) {
370
                        printk(KERN_WARNING "cosa: unable to get major %d\n",
371
                                cosa_major);
372
                        err = -EIO;
373
                        goto out;
374
                }
375
        } else {
376
                if (!(cosa_major=register_chrdev(0, "cosa", &cosa_fops))) {
377
                        printk(KERN_WARNING "cosa: unable to register chardev\n");
378
                        err = -EIO;
379
                        goto out;
380
                }
381
        }
382
        for (i=0; i<MAX_CARDS; i++)
383
                cosa_cards[i].num = -1;
384
        for (i=0; io[i] != 0 && i < MAX_CARDS; i++)
385
                cosa_probe(io[i], irq[i], dma[i]);
386
        if (!nr_cards) {
387
                printk(KERN_WARNING "cosa: no devices found.\n");
388
                unregister_chrdev(cosa_major, "cosa");
389
                err = -ENODEV;
390
                goto out;
391
        }
392
        cosa_class = class_create(THIS_MODULE, "cosa");
393
        if (IS_ERR(cosa_class)) {
394
                err = PTR_ERR(cosa_class);
395
                goto out_chrdev;
396
        }
397
        for (i=0; i<nr_cards; i++) {
398
                class_device_create(cosa_class, NULL, MKDEV(cosa_major, i),
399
                                NULL, "cosa%d", i);
400
        }
401
        err = 0;
402
        goto out;
403
 
404
out_chrdev:
405
        unregister_chrdev(cosa_major, "cosa");
406
out:
407
        return err;
408
}
409
module_init(cosa_init);
410
 
411
static void __exit cosa_exit(void)
412
{
413
        struct cosa_data *cosa;
414
        int i;
415
        printk(KERN_INFO "Unloading the cosa module\n");
416
 
417
        for (i=0; i<nr_cards; i++)
418
                class_device_destroy(cosa_class, MKDEV(cosa_major, i));
419
        class_destroy(cosa_class);
420
        for (cosa=cosa_cards; nr_cards--; cosa++) {
421
                /* Clean up the per-channel data */
422
                for (i=0; i<cosa->nchannels; i++) {
423
                        /* Chardev driver has no alloc'd per-channel data */
424
                        sppp_channel_delete(cosa->chan+i);
425
                }
426
                /* Clean up the per-card data */
427
                kfree(cosa->chan);
428
                kfree(cosa->bouncebuf);
429
                free_irq(cosa->irq, cosa);
430
                free_dma(cosa->dma);
431
                release_region(cosa->datareg,is_8bit(cosa)?2:4);
432
        }
433
        unregister_chrdev(cosa_major, "cosa");
434
}
435
module_exit(cosa_exit);
436
 
437
/*
438
 * This function should register all the net devices needed for the
439
 * single channel.
440
 */
441
static __inline__ void channel_init(struct channel_data *chan)
442
{
443
        sprintf(chan->name, "cosa%dc%d", chan->cosa->num, chan->num);
444
 
445
        /* Initialize the chardev data structures */
446
        chardev_channel_init(chan);
447
 
448
        /* Register the sppp interface */
449
        sppp_channel_init(chan);
450
}
451
 
452
static int cosa_probe(int base, int irq, int dma)
453
{
454
        struct cosa_data *cosa = cosa_cards+nr_cards;
455
        int i, err = 0;
456
 
457
        memset(cosa, 0, sizeof(struct cosa_data));
458
 
459
        /* Checking validity of parameters: */
460
        /* IRQ should be 2-7 or 10-15; negative IRQ means autoprobe */
461
        if ((irq >= 0  && irq < 2) || irq > 15 || (irq < 10 && irq > 7)) {
462
                printk (KERN_INFO "cosa_probe: invalid IRQ %d\n", irq);
463
                return -1;
464
        }
465
        /* I/O address should be between 0x100 and 0x3ff and should be
466
         * multiple of 8. */
467
        if (base < 0x100 || base > 0x3ff || base & 0x7) {
468
                printk (KERN_INFO "cosa_probe: invalid I/O address 0x%x\n",
469
                        base);
470
                return -1;
471
        }
472
        /* DMA should be 0,1 or 3-7 */
473
        if (dma < 0 || dma == 4 || dma > 7) {
474
                printk (KERN_INFO "cosa_probe: invalid DMA %d\n", dma);
475
                return -1;
476
        }
477
        /* and finally, on 16-bit COSA DMA should be 4-7 and
478
         * I/O base should not be multiple of 0x10 */
479
        if (((base & 0x8) && dma < 4) || (!(base & 0x8) && dma > 3)) {
480
                printk (KERN_INFO "cosa_probe: 8/16 bit base and DMA mismatch"
481
                        " (base=0x%x, dma=%d)\n", base, dma);
482
                return -1;
483
        }
484
 
485
        cosa->dma = dma;
486
        cosa->datareg = base;
487
        cosa->statusreg = is_8bit(cosa)?base+1:base+2;
488
        spin_lock_init(&cosa->lock);
489
 
490
        if (!request_region(base, is_8bit(cosa)?2:4,"cosa"))
491
                return -1;
492
 
493
        if (cosa_reset_and_read_id(cosa, cosa->id_string) < 0) {
494
                printk(KERN_DEBUG "cosa: probe at 0x%x failed.\n", base);
495
                err = -1;
496
                goto err_out;
497
        }
498
 
499
        /* Test the validity of identification string */
500
        if (!strncmp(cosa->id_string, "SRP", 3))
501
                cosa->type = "srp";
502
        else if (!strncmp(cosa->id_string, "COSA", 4))
503
                cosa->type = is_8bit(cosa)? "cosa8": "cosa16";
504
        else {
505
/* Print a warning only if we are not autoprobing */
506
#ifndef COSA_ISA_AUTOPROBE
507
                printk(KERN_INFO "cosa: valid signature not found at 0x%x.\n",
508
                        base);
509
#endif
510
                err = -1;
511
                goto err_out;
512
        }
513
        /* Update the name of the region now we know the type of card */
514
        release_region(base, is_8bit(cosa)?2:4);
515
        if (!request_region(base, is_8bit(cosa)?2:4, cosa->type)) {
516
                printk(KERN_DEBUG "cosa: changing name at 0x%x failed.\n", base);
517
                return -1;
518
        }
519
 
520
        /* Now do IRQ autoprobe */
521
        if (irq < 0) {
522
                unsigned long irqs;
523
/*              printk(KERN_INFO "IRQ autoprobe\n"); */
524
                irqs = probe_irq_on();
525
                /*
526
                 * Enable interrupt on tx buffer empty (it sure is)
527
                 * really sure ?
528
                 * FIXME: When this code is not used as module, we should
529
                 * probably call udelay() instead of the interruptible sleep.
530
                 */
531
                set_current_state(TASK_INTERRUPTIBLE);
532
                cosa_putstatus(cosa, SR_TX_INT_ENA);
533
                schedule_timeout(30);
534
                irq = probe_irq_off(irqs);
535
                /* Disable all IRQs from the card */
536
                cosa_putstatus(cosa, 0);
537
                /* Empty the received data register */
538
                cosa_getdata8(cosa);
539
 
540
                if (irq < 0) {
541
                        printk (KERN_INFO "cosa IRQ autoprobe: multiple interrupts obtained (%d, board at 0x%x)\n",
542
                                irq, cosa->datareg);
543
                        err = -1;
544
                        goto err_out;
545
                }
546
                if (irq == 0) {
547
                        printk (KERN_INFO "cosa IRQ autoprobe: no interrupt obtained (board at 0x%x)\n",
548
                                cosa->datareg);
549
                /*      return -1; */
550
                }
551
        }
552
 
553
        cosa->irq = irq;
554
        cosa->num = nr_cards;
555
        cosa->usage = 0;
556
        cosa->nchannels = 2;    /* FIXME: how to determine this? */
557
 
558
        if (request_irq(cosa->irq, cosa_interrupt, 0, cosa->type, cosa)) {
559
                err = -1;
560
                goto err_out;
561
        }
562
        if (request_dma(cosa->dma, cosa->type)) {
563
                err = -1;
564
                goto err_out1;
565
        }
566
 
567
        cosa->bouncebuf = kmalloc(COSA_MTU, GFP_KERNEL|GFP_DMA);
568
        if (!cosa->bouncebuf) {
569
                err = -ENOMEM;
570
                goto err_out2;
571
        }
572
        sprintf(cosa->name, "cosa%d", cosa->num);
573
 
574
        /* Initialize the per-channel data */
575
        cosa->chan = kcalloc(cosa->nchannels, sizeof(struct channel_data), GFP_KERNEL);
576
        if (!cosa->chan) {
577
                err = -ENOMEM;
578
                goto err_out3;
579
        }
580
        for (i=0; i<cosa->nchannels; i++) {
581
                cosa->chan[i].cosa = cosa;
582
                cosa->chan[i].num = i;
583
                channel_init(cosa->chan+i);
584
        }
585
 
586
        printk (KERN_INFO "cosa%d: %s (%s at 0x%x irq %d dma %d), %d channels\n",
587
                cosa->num, cosa->id_string, cosa->type,
588
                cosa->datareg, cosa->irq, cosa->dma, cosa->nchannels);
589
 
590
        return nr_cards++;
591
err_out3:
592
        kfree(cosa->bouncebuf);
593
err_out2:
594
        free_dma(cosa->dma);
595
err_out1:
596
        free_irq(cosa->irq, cosa);
597
err_out:
598
        release_region(cosa->datareg,is_8bit(cosa)?2:4);
599
        printk(KERN_NOTICE "cosa%d: allocating resources failed\n",
600
               cosa->num);
601
        return err;
602
}
603
 
604
 
605
/*---------- SPPP/HDLC netdevice ---------- */
606
 
607
static void cosa_setup(struct net_device *d)
608
{
609
        d->open = cosa_sppp_open;
610
        d->stop = cosa_sppp_close;
611
        d->hard_start_xmit = cosa_sppp_tx;
612
        d->do_ioctl = cosa_sppp_ioctl;
613
        d->get_stats = cosa_net_stats;
614
        d->tx_timeout = cosa_sppp_timeout;
615
        d->watchdog_timeo = TX_TIMEOUT;
616
}
617
 
618
static void sppp_channel_init(struct channel_data *chan)
619
{
620
        struct net_device *d;
621
        chan->if_ptr = &chan->pppdev;
622
        d = alloc_netdev(0, chan->name, cosa_setup);
623
        if (!d) {
624
                printk(KERN_WARNING "%s: alloc_netdev failed.\n", chan->name);
625
                return;
626
        }
627
        chan->pppdev.dev = d;
628
        d->base_addr = chan->cosa->datareg;
629
        d->irq = chan->cosa->irq;
630
        d->dma = chan->cosa->dma;
631
        d->priv = chan;
632
        sppp_attach(&chan->pppdev);
633
        if (register_netdev(d)) {
634
                printk(KERN_WARNING "%s: register_netdev failed.\n", d->name);
635
                sppp_detach(d);
636
                free_netdev(d);
637
                chan->pppdev.dev = NULL;
638
                return;
639
        }
640
}
641
 
642
static void sppp_channel_delete(struct channel_data *chan)
643
{
644
        unregister_netdev(chan->pppdev.dev);
645
        sppp_detach(chan->pppdev.dev);
646
        free_netdev(chan->pppdev.dev);
647
        chan->pppdev.dev = NULL;
648
}
649
 
650
static int cosa_sppp_open(struct net_device *d)
651
{
652
        struct channel_data *chan = d->priv;
653
        int err;
654
        unsigned long flags;
655
 
656
        if (!(chan->cosa->firmware_status & COSA_FW_START)) {
657
                printk(KERN_NOTICE "%s: start the firmware first (status %d)\n",
658
                        chan->cosa->name, chan->cosa->firmware_status);
659
                return -EPERM;
660
        }
661
        spin_lock_irqsave(&chan->cosa->lock, flags);
662
        if (chan->usage != 0) {
663
                printk(KERN_WARNING "%s: sppp_open called with usage count %d\n",
664
                        chan->name, chan->usage);
665
                spin_unlock_irqrestore(&chan->cosa->lock, flags);
666
                return -EBUSY;
667
        }
668
        chan->setup_rx = sppp_setup_rx;
669
        chan->tx_done = sppp_tx_done;
670
        chan->rx_done = sppp_rx_done;
671
        chan->usage=-1;
672
        chan->cosa->usage++;
673
        spin_unlock_irqrestore(&chan->cosa->lock, flags);
674
 
675
        err = sppp_open(d);
676
        if (err) {
677
                spin_lock_irqsave(&chan->cosa->lock, flags);
678
                chan->usage=0;
679
                chan->cosa->usage--;
680
 
681
                spin_unlock_irqrestore(&chan->cosa->lock, flags);
682
                return err;
683
        }
684
 
685
        netif_start_queue(d);
686
        cosa_enable_rx(chan);
687
        return 0;
688
}
689
 
690
static int cosa_sppp_tx(struct sk_buff *skb, struct net_device *dev)
691
{
692
        struct channel_data *chan = dev->priv;
693
 
694
        netif_stop_queue(dev);
695
 
696
        chan->tx_skb = skb;
697
        cosa_start_tx(chan, skb->data, skb->len);
698
        return 0;
699
}
700
 
701
static void cosa_sppp_timeout(struct net_device *dev)
702
{
703
        struct channel_data *chan = dev->priv;
704
 
705
        if (test_bit(RXBIT, &chan->cosa->rxtx)) {
706
                chan->stats.rx_errors++;
707
                chan->stats.rx_missed_errors++;
708
        } else {
709
                chan->stats.tx_errors++;
710
                chan->stats.tx_aborted_errors++;
711
        }
712
        cosa_kick(chan->cosa);
713
        if (chan->tx_skb) {
714
                dev_kfree_skb(chan->tx_skb);
715
                chan->tx_skb = NULL;
716
        }
717
        netif_wake_queue(dev);
718
}
719
 
720
static int cosa_sppp_close(struct net_device *d)
721
{
722
        struct channel_data *chan = d->priv;
723
        unsigned long flags;
724
 
725
        netif_stop_queue(d);
726
        sppp_close(d);
727
        cosa_disable_rx(chan);
728
        spin_lock_irqsave(&chan->cosa->lock, flags);
729
        if (chan->rx_skb) {
730
                kfree_skb(chan->rx_skb);
731
                chan->rx_skb = NULL;
732
        }
733
        if (chan->tx_skb) {
734
                kfree_skb(chan->tx_skb);
735
                chan->tx_skb = NULL;
736
        }
737
        chan->usage=0;
738
        chan->cosa->usage--;
739
        spin_unlock_irqrestore(&chan->cosa->lock, flags);
740
        return 0;
741
}
742
 
743
static char *sppp_setup_rx(struct channel_data *chan, int size)
744
{
745
        /*
746
         * We can safely fall back to non-dma-able memory, because we have
747
         * the cosa->bouncebuf pre-allocated.
748
         */
749
        if (chan->rx_skb)
750
                kfree_skb(chan->rx_skb);
751
        chan->rx_skb = dev_alloc_skb(size);
752
        if (chan->rx_skb == NULL) {
753
                printk(KERN_NOTICE "%s: Memory squeeze, dropping packet\n",
754
                        chan->name);
755
                chan->stats.rx_dropped++;
756
                return NULL;
757
        }
758
        chan->pppdev.dev->trans_start = jiffies;
759
        return skb_put(chan->rx_skb, size);
760
}
761
 
762
static int sppp_rx_done(struct channel_data *chan)
763
{
764
        if (!chan->rx_skb) {
765
                printk(KERN_WARNING "%s: rx_done with empty skb!\n",
766
                        chan->name);
767
                chan->stats.rx_errors++;
768
                chan->stats.rx_frame_errors++;
769
                return 0;
770
        }
771
        chan->rx_skb->protocol = htons(ETH_P_WAN_PPP);
772
        chan->rx_skb->dev = chan->pppdev.dev;
773
        skb_reset_mac_header(chan->rx_skb);
774
        chan->stats.rx_packets++;
775
        chan->stats.rx_bytes += chan->cosa->rxsize;
776
        netif_rx(chan->rx_skb);
777
        chan->rx_skb = NULL;
778
        chan->pppdev.dev->last_rx = jiffies;
779
        return 0;
780
}
781
 
782
/* ARGSUSED */
783
static int sppp_tx_done(struct channel_data *chan, int size)
784
{
785
        if (!chan->tx_skb) {
786
                printk(KERN_WARNING "%s: tx_done with empty skb!\n",
787
                        chan->name);
788
                chan->stats.tx_errors++;
789
                chan->stats.tx_aborted_errors++;
790
                return 1;
791
        }
792
        dev_kfree_skb_irq(chan->tx_skb);
793
        chan->tx_skb = NULL;
794
        chan->stats.tx_packets++;
795
        chan->stats.tx_bytes += size;
796
        netif_wake_queue(chan->pppdev.dev);
797
        return 1;
798
}
799
 
800
static struct net_device_stats *cosa_net_stats(struct net_device *dev)
801
{
802
        struct channel_data *chan = dev->priv;
803
        return &chan->stats;
804
}
805
 
806
 
807
/*---------- Character device ---------- */
808
 
809
static void chardev_channel_init(struct channel_data *chan)
810
{
811
        init_MUTEX(&chan->rsem);
812
        init_MUTEX(&chan->wsem);
813
}
814
 
815
static ssize_t cosa_read(struct file *file,
816
        char __user *buf, size_t count, loff_t *ppos)
817
{
818
        DECLARE_WAITQUEUE(wait, current);
819
        unsigned long flags;
820
        struct channel_data *chan = file->private_data;
821
        struct cosa_data *cosa = chan->cosa;
822
        char *kbuf;
823
 
824
        if (!(cosa->firmware_status & COSA_FW_START)) {
825
                printk(KERN_NOTICE "%s: start the firmware first (status %d)\n",
826
                        cosa->name, cosa->firmware_status);
827
                return -EPERM;
828
        }
829
        if (down_interruptible(&chan->rsem))
830
                return -ERESTARTSYS;
831
 
832
        if ((chan->rxdata = kmalloc(COSA_MTU, GFP_DMA|GFP_KERNEL)) == NULL) {
833
                printk(KERN_INFO "%s: cosa_read() - OOM\n", cosa->name);
834
                up(&chan->rsem);
835
                return -ENOMEM;
836
        }
837
 
838
        chan->rx_status = 0;
839
        cosa_enable_rx(chan);
840
        spin_lock_irqsave(&cosa->lock, flags);
841
        add_wait_queue(&chan->rxwaitq, &wait);
842
        while(!chan->rx_status) {
843
                current->state = TASK_INTERRUPTIBLE;
844
                spin_unlock_irqrestore(&cosa->lock, flags);
845
                schedule();
846
                spin_lock_irqsave(&cosa->lock, flags);
847
                if (signal_pending(current) && chan->rx_status == 0) {
848
                        chan->rx_status = 1;
849
                        remove_wait_queue(&chan->rxwaitq, &wait);
850
                        current->state = TASK_RUNNING;
851
                        spin_unlock_irqrestore(&cosa->lock, flags);
852
                        up(&chan->rsem);
853
                        return -ERESTARTSYS;
854
                }
855
        }
856
        remove_wait_queue(&chan->rxwaitq, &wait);
857
        current->state = TASK_RUNNING;
858
        kbuf = chan->rxdata;
859
        count = chan->rxsize;
860
        spin_unlock_irqrestore(&cosa->lock, flags);
861
        up(&chan->rsem);
862
 
863
        if (copy_to_user(buf, kbuf, count)) {
864
                kfree(kbuf);
865
                return -EFAULT;
866
        }
867
        kfree(kbuf);
868
        return count;
869
}
870
 
871
static char *chrdev_setup_rx(struct channel_data *chan, int size)
872
{
873
        /* Expect size <= COSA_MTU */
874
        chan->rxsize = size;
875
        return chan->rxdata;
876
}
877
 
878
static int chrdev_rx_done(struct channel_data *chan)
879
{
880
        if (chan->rx_status) { /* Reader has died */
881
                kfree(chan->rxdata);
882
                up(&chan->wsem);
883
        }
884
        chan->rx_status = 1;
885
        wake_up_interruptible(&chan->rxwaitq);
886
        return 1;
887
}
888
 
889
 
890
static ssize_t cosa_write(struct file *file,
891
        const char __user *buf, size_t count, loff_t *ppos)
892
{
893
        DECLARE_WAITQUEUE(wait, current);
894
        struct channel_data *chan = file->private_data;
895
        struct cosa_data *cosa = chan->cosa;
896
        unsigned long flags;
897
        char *kbuf;
898
 
899
        if (!(cosa->firmware_status & COSA_FW_START)) {
900
                printk(KERN_NOTICE "%s: start the firmware first (status %d)\n",
901
                        cosa->name, cosa->firmware_status);
902
                return -EPERM;
903
        }
904
        if (down_interruptible(&chan->wsem))
905
                return -ERESTARTSYS;
906
 
907
        if (count > COSA_MTU)
908
                count = COSA_MTU;
909
 
910
        /* Allocate the buffer */
911
        if ((kbuf = kmalloc(count, GFP_KERNEL|GFP_DMA)) == NULL) {
912
                printk(KERN_NOTICE "%s: cosa_write() OOM - dropping packet\n",
913
                        cosa->name);
914
                up(&chan->wsem);
915
                return -ENOMEM;
916
        }
917
        if (copy_from_user(kbuf, buf, count)) {
918
                up(&chan->wsem);
919
                kfree(kbuf);
920
                return -EFAULT;
921
        }
922
        chan->tx_status=0;
923
        cosa_start_tx(chan, kbuf, count);
924
 
925
        spin_lock_irqsave(&cosa->lock, flags);
926
        add_wait_queue(&chan->txwaitq, &wait);
927
        while(!chan->tx_status) {
928
                current->state = TASK_INTERRUPTIBLE;
929
                spin_unlock_irqrestore(&cosa->lock, flags);
930
                schedule();
931
                spin_lock_irqsave(&cosa->lock, flags);
932
                if (signal_pending(current) && chan->tx_status == 0) {
933
                        chan->tx_status = 1;
934
                        remove_wait_queue(&chan->txwaitq, &wait);
935
                        current->state = TASK_RUNNING;
936
                        chan->tx_status = 1;
937
                        spin_unlock_irqrestore(&cosa->lock, flags);
938
                        return -ERESTARTSYS;
939
                }
940
        }
941
        remove_wait_queue(&chan->txwaitq, &wait);
942
        current->state = TASK_RUNNING;
943
        up(&chan->wsem);
944
        spin_unlock_irqrestore(&cosa->lock, flags);
945
        kfree(kbuf);
946
        return count;
947
}
948
 
949
static int chrdev_tx_done(struct channel_data *chan, int size)
950
{
951
        if (chan->tx_status) { /* Writer was interrupted */
952
                kfree(chan->txbuf);
953
                up(&chan->wsem);
954
        }
955
        chan->tx_status = 1;
956
        wake_up_interruptible(&chan->txwaitq);
957
        return 1;
958
}
959
 
960
static unsigned int cosa_poll(struct file *file, poll_table *poll)
961
{
962
        printk(KERN_INFO "cosa_poll is here\n");
963
        return 0;
964
}
965
 
966
static int cosa_open(struct inode *inode, struct file *file)
967
{
968
        struct cosa_data *cosa;
969
        struct channel_data *chan;
970
        unsigned long flags;
971
        int n;
972
 
973
        if ((n=iminor(file->f_path.dentry->d_inode)>>CARD_MINOR_BITS)
974
                >= nr_cards)
975
                return -ENODEV;
976
        cosa = cosa_cards+n;
977
 
978
        if ((n=iminor(file->f_path.dentry->d_inode)
979
                & ((1<<CARD_MINOR_BITS)-1)) >= cosa->nchannels)
980
                return -ENODEV;
981
        chan = cosa->chan + n;
982
 
983
        file->private_data = chan;
984
 
985
        spin_lock_irqsave(&cosa->lock, flags);
986
 
987
        if (chan->usage < 0) { /* in netdev mode */
988
                spin_unlock_irqrestore(&cosa->lock, flags);
989
                return -EBUSY;
990
        }
991
        cosa->usage++;
992
        chan->usage++;
993
 
994
        chan->tx_done = chrdev_tx_done;
995
        chan->setup_rx = chrdev_setup_rx;
996
        chan->rx_done = chrdev_rx_done;
997
        spin_unlock_irqrestore(&cosa->lock, flags);
998
        return 0;
999
}
1000
 
1001
static int cosa_release(struct inode *inode, struct file *file)
1002
{
1003
        struct channel_data *channel = file->private_data;
1004
        struct cosa_data *cosa;
1005
        unsigned long flags;
1006
 
1007
        cosa = channel->cosa;
1008
        spin_lock_irqsave(&cosa->lock, flags);
1009
        cosa->usage--;
1010
        channel->usage--;
1011
        spin_unlock_irqrestore(&cosa->lock, flags);
1012
        return 0;
1013
}
1014
 
1015
#ifdef COSA_FASYNC_WORKING
1016
static struct fasync_struct *fasync[256] = { NULL, };
1017
 
1018
/* To be done ... */
1019
static int cosa_fasync(struct inode *inode, struct file *file, int on)
1020
{
1021
        int port = iminor(inode);
1022
        int rv = fasync_helper(inode, file, on, &fasync[port]);
1023
        return rv < 0 ? rv : 0;
1024
}
1025
#endif
1026
 
1027
 
1028
/* ---------- Ioctls ---------- */
1029
 
1030
/*
1031
 * Ioctl subroutines can safely be made inline, because they are called
1032
 * only from cosa_ioctl().
1033
 */
1034
static inline int cosa_reset(struct cosa_data *cosa)
1035
{
1036
        char idstring[COSA_MAX_ID_STRING];
1037
        if (cosa->usage > 1)
1038
                printk(KERN_INFO "cosa%d: WARNING: reset requested with cosa->usage > 1 (%d). Odd things may happen.\n",
1039
                        cosa->num, cosa->usage);
1040
        cosa->firmware_status &= ~(COSA_FW_RESET|COSA_FW_START);
1041
        if (cosa_reset_and_read_id(cosa, idstring) < 0) {
1042
                printk(KERN_NOTICE "cosa%d: reset failed\n", cosa->num);
1043
                return -EIO;
1044
        }
1045
        printk(KERN_INFO "cosa%d: resetting device: %s\n", cosa->num,
1046
                idstring);
1047
        cosa->firmware_status |= COSA_FW_RESET;
1048
        return 0;
1049
}
1050
 
1051
/* High-level function to download data into COSA memory. Calls download() */
1052
static inline int cosa_download(struct cosa_data *cosa, void __user *arg)
1053
{
1054
        struct cosa_download d;
1055
        int i;
1056
 
1057
        if (cosa->usage > 1)
1058
                printk(KERN_INFO "%s: WARNING: download of microcode requested with cosa->usage > 1 (%d). Odd things may happen.\n",
1059
                        cosa->name, cosa->usage);
1060
        if (!(cosa->firmware_status & COSA_FW_RESET)) {
1061
                printk(KERN_NOTICE "%s: reset the card first (status %d).\n",
1062
                        cosa->name, cosa->firmware_status);
1063
                return -EPERM;
1064
        }
1065
 
1066
        if (copy_from_user(&d, arg, sizeof(d)))
1067
                return -EFAULT;
1068
 
1069
        if (d.addr < 0 || d.addr > COSA_MAX_FIRMWARE_SIZE)
1070
                return -EINVAL;
1071
        if (d.len < 0 || d.len > COSA_MAX_FIRMWARE_SIZE)
1072
                return -EINVAL;
1073
 
1074
 
1075
        /* If something fails, force the user to reset the card */
1076
        cosa->firmware_status &= ~(COSA_FW_RESET|COSA_FW_DOWNLOAD);
1077
 
1078
        i = download(cosa, d.code, d.len, d.addr);
1079
        if (i < 0) {
1080
                printk(KERN_NOTICE "cosa%d: microcode download failed: %d\n",
1081
                        cosa->num, i);
1082
                return -EIO;
1083
        }
1084
        printk(KERN_INFO "cosa%d: downloading microcode - 0x%04x bytes at 0x%04x\n",
1085
                cosa->num, d.len, d.addr);
1086
        cosa->firmware_status |= COSA_FW_RESET|COSA_FW_DOWNLOAD;
1087
        return 0;
1088
}
1089
 
1090
/* High-level function to read COSA memory. Calls readmem() */
1091
static inline int cosa_readmem(struct cosa_data *cosa, void __user *arg)
1092
{
1093
        struct cosa_download d;
1094
        int i;
1095
 
1096
        if (cosa->usage > 1)
1097
                printk(KERN_INFO "cosa%d: WARNING: readmem requested with "
1098
                        "cosa->usage > 1 (%d). Odd things may happen.\n",
1099
                        cosa->num, cosa->usage);
1100
        if (!(cosa->firmware_status & COSA_FW_RESET)) {
1101
                printk(KERN_NOTICE "%s: reset the card first (status %d).\n",
1102
                        cosa->name, cosa->firmware_status);
1103
                return -EPERM;
1104
        }
1105
 
1106
        if (copy_from_user(&d, arg, sizeof(d)))
1107
                return -EFAULT;
1108
 
1109
        /* If something fails, force the user to reset the card */
1110
        cosa->firmware_status &= ~COSA_FW_RESET;
1111
 
1112
        i = readmem(cosa, d.code, d.len, d.addr);
1113
        if (i < 0) {
1114
                printk(KERN_NOTICE "cosa%d: reading memory failed: %d\n",
1115
                        cosa->num, i);
1116
                return -EIO;
1117
        }
1118
        printk(KERN_INFO "cosa%d: reading card memory - 0x%04x bytes at 0x%04x\n",
1119
                cosa->num, d.len, d.addr);
1120
        cosa->firmware_status |= COSA_FW_RESET;
1121
        return 0;
1122
}
1123
 
1124
/* High-level function to start microcode. Calls startmicrocode(). */
1125
static inline int cosa_start(struct cosa_data *cosa, int address)
1126
{
1127
        int i;
1128
 
1129
        if (cosa->usage > 1)
1130
                printk(KERN_INFO "cosa%d: WARNING: start microcode requested with cosa->usage > 1 (%d). Odd things may happen.\n",
1131
                        cosa->num, cosa->usage);
1132
 
1133
        if ((cosa->firmware_status & (COSA_FW_RESET|COSA_FW_DOWNLOAD))
1134
                != (COSA_FW_RESET|COSA_FW_DOWNLOAD)) {
1135
                printk(KERN_NOTICE "%s: download the microcode and/or reset the card first (status %d).\n",
1136
                        cosa->name, cosa->firmware_status);
1137
                return -EPERM;
1138
        }
1139
        cosa->firmware_status &= ~COSA_FW_RESET;
1140
        if ((i=startmicrocode(cosa, address)) < 0) {
1141
                printk(KERN_NOTICE "cosa%d: start microcode at 0x%04x failed: %d\n",
1142
                        cosa->num, address, i);
1143
                return -EIO;
1144
        }
1145
        printk(KERN_INFO "cosa%d: starting microcode at 0x%04x\n",
1146
                cosa->num, address);
1147
        cosa->startaddr = address;
1148
        cosa->firmware_status |= COSA_FW_START;
1149
        return 0;
1150
}
1151
 
1152
/* Buffer of size at least COSA_MAX_ID_STRING is expected */
1153
static inline int cosa_getidstr(struct cosa_data *cosa, char __user *string)
1154
{
1155
        int l = strlen(cosa->id_string)+1;
1156
        if (copy_to_user(string, cosa->id_string, l))
1157
                return -EFAULT;
1158
        return l;
1159
}
1160
 
1161
/* Buffer of size at least COSA_MAX_ID_STRING is expected */
1162
static inline int cosa_gettype(struct cosa_data *cosa, char __user *string)
1163
{
1164
        int l = strlen(cosa->type)+1;
1165
        if (copy_to_user(string, cosa->type, l))
1166
                return -EFAULT;
1167
        return l;
1168
}
1169
 
1170
static int cosa_ioctl_common(struct cosa_data *cosa,
1171
        struct channel_data *channel, unsigned int cmd, unsigned long arg)
1172
{
1173
        void __user *argp = (void __user *)arg;
1174
        switch(cmd) {
1175
        case COSAIORSET:        /* Reset the device */
1176
                if (!capable(CAP_NET_ADMIN))
1177
                        return -EACCES;
1178
                return cosa_reset(cosa);
1179
        case COSAIOSTRT:        /* Start the firmware */
1180
                if (!capable(CAP_SYS_RAWIO))
1181
                        return -EACCES;
1182
                return cosa_start(cosa, arg);
1183
        case COSAIODOWNLD:      /* Download the firmware */
1184
                if (!capable(CAP_SYS_RAWIO))
1185
                        return -EACCES;
1186
 
1187
                return cosa_download(cosa, argp);
1188
        case COSAIORMEM:
1189
                if (!capable(CAP_SYS_RAWIO))
1190
                        return -EACCES;
1191
                return cosa_readmem(cosa, argp);
1192
        case COSAIORTYPE:
1193
                return cosa_gettype(cosa, argp);
1194
        case COSAIORIDSTR:
1195
                return cosa_getidstr(cosa, argp);
1196
        case COSAIONRCARDS:
1197
                return nr_cards;
1198
        case COSAIONRCHANS:
1199
                return cosa->nchannels;
1200
        case COSAIOBMSET:
1201
                if (!capable(CAP_SYS_RAWIO))
1202
                        return -EACCES;
1203
                if (is_8bit(cosa))
1204
                        return -EINVAL;
1205
                if (arg != COSA_BM_OFF && arg != COSA_BM_ON)
1206
                        return -EINVAL;
1207
                cosa->busmaster = arg;
1208
                return 0;
1209
        case COSAIOBMGET:
1210
                return cosa->busmaster;
1211
        }
1212
        return -ENOIOCTLCMD;
1213
}
1214
 
1215
static int cosa_sppp_ioctl(struct net_device *dev, struct ifreq *ifr,
1216
        int cmd)
1217
{
1218
        int rv;
1219
        struct channel_data *chan = dev->priv;
1220
        rv = cosa_ioctl_common(chan->cosa, chan, cmd, (unsigned long)ifr->ifr_data);
1221
        if (rv == -ENOIOCTLCMD) {
1222
                return sppp_do_ioctl(dev, ifr, cmd);
1223
        }
1224
        return rv;
1225
}
1226
 
1227
static int cosa_chardev_ioctl(struct inode *inode, struct file *file,
1228
        unsigned int cmd, unsigned long arg)
1229
{
1230
        struct channel_data *channel = file->private_data;
1231
        struct cosa_data *cosa = channel->cosa;
1232
        return cosa_ioctl_common(cosa, channel, cmd, arg);
1233
}
1234
 
1235
 
1236
/*---------- HW layer interface ---------- */
1237
 
1238
/*
1239
 * The higher layer can bind itself to the HW layer by setting the callbacks
1240
 * in the channel_data structure and by using these routines.
1241
 */
1242
static void cosa_enable_rx(struct channel_data *chan)
1243
{
1244
        struct cosa_data *cosa = chan->cosa;
1245
 
1246
        if (!test_and_set_bit(chan->num, &cosa->rxbitmap))
1247
                put_driver_status(cosa);
1248
}
1249
 
1250
static void cosa_disable_rx(struct channel_data *chan)
1251
{
1252
        struct cosa_data *cosa = chan->cosa;
1253
 
1254
        if (test_and_clear_bit(chan->num, &cosa->rxbitmap))
1255
                put_driver_status(cosa);
1256
}
1257
 
1258
/*
1259
 * FIXME: This routine probably should check for cosa_start_tx() called when
1260
 * the previous transmit is still unfinished. In this case the non-zero
1261
 * return value should indicate to the caller that the queuing(sp?) up
1262
 * the transmit has failed.
1263
 */
1264
static int cosa_start_tx(struct channel_data *chan, char *buf, int len)
1265
{
1266
        struct cosa_data *cosa = chan->cosa;
1267
        unsigned long flags;
1268
#ifdef DEBUG_DATA
1269
        int i;
1270
 
1271
        printk(KERN_INFO "cosa%dc%d: starting tx(0x%x)", chan->cosa->num,
1272
                chan->num, len);
1273
        for (i=0; i<len; i++)
1274
                printk(" %02x", buf[i]&0xff);
1275
        printk("\n");
1276
#endif
1277
        spin_lock_irqsave(&cosa->lock, flags);
1278
        chan->txbuf = buf;
1279
        chan->txsize = len;
1280
        if (len > COSA_MTU)
1281
                chan->txsize = COSA_MTU;
1282
        spin_unlock_irqrestore(&cosa->lock, flags);
1283
 
1284
        /* Tell the firmware we are ready */
1285
        set_bit(chan->num, &cosa->txbitmap);
1286
        put_driver_status(cosa);
1287
 
1288
        return 0;
1289
}
1290
 
1291
static void put_driver_status(struct cosa_data *cosa)
1292
{
1293
        unsigned long flags;
1294
        int status;
1295
 
1296
        spin_lock_irqsave(&cosa->lock, flags);
1297
 
1298
        status = (cosa->rxbitmap ? DRIVER_RX_READY : 0)
1299
                | (cosa->txbitmap ? DRIVER_TX_READY : 0)
1300
                | (cosa->txbitmap? ~(cosa->txbitmap<<DRIVER_TXMAP_SHIFT)
1301
                        &DRIVER_TXMAP_MASK : 0);
1302
        if (!cosa->rxtx) {
1303
                if (cosa->rxbitmap|cosa->txbitmap) {
1304
                        if (!cosa->enabled) {
1305
                                cosa_putstatus(cosa, SR_RX_INT_ENA);
1306
#ifdef DEBUG_IO
1307
                                debug_status_out(cosa, SR_RX_INT_ENA);
1308
#endif
1309
                                cosa->enabled = 1;
1310
                        }
1311
                } else if (cosa->enabled) {
1312
                        cosa->enabled = 0;
1313
                        cosa_putstatus(cosa, 0);
1314
#ifdef DEBUG_IO
1315
                        debug_status_out(cosa, 0);
1316
#endif
1317
                }
1318
                cosa_putdata8(cosa, status);
1319
#ifdef DEBUG_IO
1320
                debug_data_cmd(cosa, status);
1321
#endif
1322
        }
1323
        spin_unlock_irqrestore(&cosa->lock, flags);
1324
}
1325
 
1326
static void put_driver_status_nolock(struct cosa_data *cosa)
1327
{
1328
        int status;
1329
 
1330
        status = (cosa->rxbitmap ? DRIVER_RX_READY : 0)
1331
                | (cosa->txbitmap ? DRIVER_TX_READY : 0)
1332
                | (cosa->txbitmap? ~(cosa->txbitmap<<DRIVER_TXMAP_SHIFT)
1333
                        &DRIVER_TXMAP_MASK : 0);
1334
 
1335
        if (cosa->rxbitmap|cosa->txbitmap) {
1336
                cosa_putstatus(cosa, SR_RX_INT_ENA);
1337
#ifdef DEBUG_IO
1338
                debug_status_out(cosa, SR_RX_INT_ENA);
1339
#endif
1340
                cosa->enabled = 1;
1341
        } else {
1342
                cosa_putstatus(cosa, 0);
1343
#ifdef DEBUG_IO
1344
                debug_status_out(cosa, 0);
1345
#endif
1346
                cosa->enabled = 0;
1347
        }
1348
        cosa_putdata8(cosa, status);
1349
#ifdef DEBUG_IO
1350
        debug_data_cmd(cosa, status);
1351
#endif
1352
}
1353
 
1354
/*
1355
 * The "kickme" function: When the DMA times out, this is called to
1356
 * clean up the driver status.
1357
 * FIXME: Preliminary support, the interface is probably wrong.
1358
 */
1359
static void cosa_kick(struct cosa_data *cosa)
1360
{
1361
        unsigned long flags, flags1;
1362
        char *s = "(probably) IRQ";
1363
 
1364
        if (test_bit(RXBIT, &cosa->rxtx))
1365
                s = "RX DMA";
1366
        if (test_bit(TXBIT, &cosa->rxtx))
1367
                s = "TX DMA";
1368
 
1369
        printk(KERN_INFO "%s: %s timeout - restarting.\n", cosa->name, s);
1370
        spin_lock_irqsave(&cosa->lock, flags);
1371
        cosa->rxtx = 0;
1372
 
1373
        flags1 = claim_dma_lock();
1374
        disable_dma(cosa->dma);
1375
        clear_dma_ff(cosa->dma);
1376
        release_dma_lock(flags1);
1377
 
1378
        /* FIXME: Anything else? */
1379
        udelay(100);
1380
        cosa_putstatus(cosa, 0);
1381
        udelay(100);
1382
        (void) cosa_getdata8(cosa);
1383
        udelay(100);
1384
        cosa_putdata8(cosa, 0);
1385
        udelay(100);
1386
        put_driver_status_nolock(cosa);
1387
        spin_unlock_irqrestore(&cosa->lock, flags);
1388
}
1389
 
1390
/*
1391
 * Check if the whole buffer is DMA-able. It means it is below the 16M of
1392
 * physical memory and doesn't span the 64k boundary. For now it seems
1393
 * SKB's never do this, but we'll check this anyway.
1394
 */
1395
static int cosa_dma_able(struct channel_data *chan, char *buf, int len)
1396
{
1397
        static int count;
1398
        unsigned long b = (unsigned long)buf;
1399
        if (b+len >= MAX_DMA_ADDRESS)
1400
                return 0;
1401
        if ((b^ (b+len)) & 0x10000) {
1402
                if (count++ < 5)
1403
                        printk(KERN_INFO "%s: packet spanning a 64k boundary\n",
1404
                                chan->name);
1405
                return 0;
1406
        }
1407
        return 1;
1408
}
1409
 
1410
 
1411
/* ---------- The SRP/COSA ROM monitor functions ---------- */
1412
 
1413
/*
1414
 * Downloading SRP microcode: say "w" to SRP monitor, it answers by "w=",
1415
 * drivers need to say 4-digit hex number meaning start address of the microcode
1416
 * separated by a single space. Monitor replies by saying " =". Now driver
1417
 * has to write 4-digit hex number meaning the last byte address ended
1418
 * by a single space. Monitor has to reply with a space. Now the download
1419
 * begins. After the download monitor replies with "\r\n." (CR LF dot).
1420
 */
1421
static int download(struct cosa_data *cosa, const char __user *microcode, int length, int address)
1422
{
1423
        int i;
1424
 
1425
        if (put_wait_data(cosa, 'w') == -1) return -1;
1426
        if ((i=get_wait_data(cosa)) != 'w') { printk("dnld: 0x%04x\n",i); return -2;}
1427
        if (get_wait_data(cosa) != '=') return -3;
1428
 
1429
        if (puthexnumber(cosa, address) < 0) return -4;
1430
        if (put_wait_data(cosa, ' ') == -1) return -10;
1431
        if (get_wait_data(cosa) != ' ') return -11;
1432
        if (get_wait_data(cosa) != '=') return -12;
1433
 
1434
        if (puthexnumber(cosa, address+length-1) < 0) return -13;
1435
        if (put_wait_data(cosa, ' ') == -1) return -18;
1436
        if (get_wait_data(cosa) != ' ') return -19;
1437
 
1438
        while (length--) {
1439
                char c;
1440
#ifndef SRP_DOWNLOAD_AT_BOOT
1441
                if (get_user(c, microcode))
1442
                        return -23; /* ??? */
1443
#else
1444
                c = *microcode;
1445
#endif
1446
                if (put_wait_data(cosa, c) == -1)
1447
                        return -20;
1448
                microcode++;
1449
        }
1450
 
1451
        if (get_wait_data(cosa) != '\r') return -21;
1452
        if (get_wait_data(cosa) != '\n') return -22;
1453
        if (get_wait_data(cosa) != '.') return -23;
1454
#if 0
1455
        printk(KERN_DEBUG "cosa%d: download completed.\n", cosa->num);
1456
#endif
1457
        return 0;
1458
}
1459
 
1460
 
1461
/*
1462
 * Starting microcode is done via the "g" command of the SRP monitor.
1463
 * The chat should be the following: "g" "g=" "<addr><CR>"
1464
 * "<CR><CR><LF><CR><LF>".
1465
 */
1466
static int startmicrocode(struct cosa_data *cosa, int address)
1467
{
1468
        if (put_wait_data(cosa, 'g') == -1) return -1;
1469
        if (get_wait_data(cosa) != 'g') return -2;
1470
        if (get_wait_data(cosa) != '=') return -3;
1471
 
1472
        if (puthexnumber(cosa, address) < 0) return -4;
1473
        if (put_wait_data(cosa, '\r') == -1) return -5;
1474
 
1475
        if (get_wait_data(cosa) != '\r') return -6;
1476
        if (get_wait_data(cosa) != '\r') return -7;
1477
        if (get_wait_data(cosa) != '\n') return -8;
1478
        if (get_wait_data(cosa) != '\r') return -9;
1479
        if (get_wait_data(cosa) != '\n') return -10;
1480
#if 0
1481
        printk(KERN_DEBUG "cosa%d: microcode started\n", cosa->num);
1482
#endif
1483
        return 0;
1484
}
1485
 
1486
/*
1487
 * Reading memory is done via the "r" command of the SRP monitor.
1488
 * The chat is the following "r" "r=" "<addr> " " =" "<last_byte> " " "
1489
 * Then driver can read the data and the conversation is finished
1490
 * by SRP monitor sending "<CR><LF>." (dot at the end).
1491
 *
1492
 * This routine is not needed during the normal operation and serves
1493
 * for debugging purposes only.
1494
 */
1495
static int readmem(struct cosa_data *cosa, char __user *microcode, int length, int address)
1496
{
1497
        if (put_wait_data(cosa, 'r') == -1) return -1;
1498
        if ((get_wait_data(cosa)) != 'r') return -2;
1499
        if ((get_wait_data(cosa)) != '=') return -3;
1500
 
1501
        if (puthexnumber(cosa, address) < 0) return -4;
1502
        if (put_wait_data(cosa, ' ') == -1) return -5;
1503
        if (get_wait_data(cosa) != ' ') return -6;
1504
        if (get_wait_data(cosa) != '=') return -7;
1505
 
1506
        if (puthexnumber(cosa, address+length-1) < 0) return -8;
1507
        if (put_wait_data(cosa, ' ') == -1) return -9;
1508
        if (get_wait_data(cosa) != ' ') return -10;
1509
 
1510
        while (length--) {
1511
                char c;
1512
                int i;
1513
                if ((i=get_wait_data(cosa)) == -1) {
1514
                        printk (KERN_INFO "cosa: 0x%04x bytes remaining\n",
1515
                                length);
1516
                        return -11;
1517
                }
1518
                c=i;
1519
#if 1
1520
                if (put_user(c, microcode))
1521
                        return -23; /* ??? */
1522
#else
1523
                *microcode = c;
1524
#endif
1525
                microcode++;
1526
        }
1527
 
1528
        if (get_wait_data(cosa) != '\r') return -21;
1529
        if (get_wait_data(cosa) != '\n') return -22;
1530
        if (get_wait_data(cosa) != '.') return -23;
1531
#if 0
1532
        printk(KERN_DEBUG "cosa%d: readmem completed.\n", cosa->num);
1533
#endif
1534
        return 0;
1535
}
1536
 
1537
/*
1538
 * This function resets the device and reads the initial prompt
1539
 * of the device's ROM monitor.
1540
 */
1541
static int cosa_reset_and_read_id(struct cosa_data *cosa, char *idstring)
1542
{
1543
        int i=0, id=0, prev=0, curr=0;
1544
 
1545
        /* Reset the card ... */
1546
        cosa_putstatus(cosa, 0);
1547
        cosa_getdata8(cosa);
1548
        cosa_putstatus(cosa, SR_RST);
1549
#ifdef MODULE
1550
        msleep(500);
1551
#else
1552
        udelay(5*100000);
1553
#endif
1554
        /* Disable all IRQs from the card */
1555
        cosa_putstatus(cosa, 0);
1556
 
1557
        /*
1558
         * Try to read the ID string. The card then prints out the
1559
         * identification string ended by the "\n\x2e".
1560
         *
1561
         * The following loop is indexed through i (instead of id)
1562
         * to avoid looping forever when for any reason
1563
         * the port returns '\r', '\n' or '\x2e' permanently.
1564
         */
1565
        for (i=0; i<COSA_MAX_ID_STRING-1; i++, prev=curr) {
1566
                if ((curr = get_wait_data(cosa)) == -1) {
1567
                        return -1;
1568
                }
1569
                curr &= 0xff;
1570
                if (curr != '\r' && curr != '\n' && curr != 0x2e)
1571
                        idstring[id++] = curr;
1572
                if (curr == 0x2e && prev == '\n')
1573
                        break;
1574
        }
1575
        /* Perhaps we should fail when i==COSA_MAX_ID_STRING-1 ? */
1576
        idstring[id] = '\0';
1577
        return id;
1578
}
1579
 
1580
 
1581
/* ---------- Auxiliary routines for COSA/SRP monitor ---------- */
1582
 
1583
/*
1584
 * This routine gets the data byte from the card waiting for the SR_RX_RDY
1585
 * bit to be set in a loop. It should be used in the exceptional cases
1586
 * only (for example when resetting the card or downloading the firmware.
1587
 */
1588
static int get_wait_data(struct cosa_data *cosa)
1589
{
1590
        int retries = 1000;
1591
 
1592
        while (--retries) {
1593
                /* read data and return them */
1594
                if (cosa_getstatus(cosa) & SR_RX_RDY) {
1595
                        short r;
1596
                        r = cosa_getdata8(cosa);
1597
#if 0
1598
                        printk(KERN_INFO "cosa: get_wait_data returning after %d retries\n", 999-retries);
1599
#endif
1600
                        return r;
1601
                }
1602
                /* sleep if not ready to read */
1603
                schedule_timeout_interruptible(1);
1604
        }
1605
        printk(KERN_INFO "cosa: timeout in get_wait_data (status 0x%x)\n",
1606
                cosa_getstatus(cosa));
1607
        return -1;
1608
}
1609
 
1610
/*
1611
 * This routine puts the data byte to the card waiting for the SR_TX_RDY
1612
 * bit to be set in a loop. It should be used in the exceptional cases
1613
 * only (for example when resetting the card or downloading the firmware).
1614
 */
1615
static int put_wait_data(struct cosa_data *cosa, int data)
1616
{
1617
        int retries = 1000;
1618
        while (--retries) {
1619
                /* read data and return them */
1620
                if (cosa_getstatus(cosa) & SR_TX_RDY) {
1621
                        cosa_putdata8(cosa, data);
1622
#if 0
1623
                        printk(KERN_INFO "Putdata: %d retries\n", 999-retries);
1624
#endif
1625
                        return 0;
1626
                }
1627
#if 0
1628
                /* sleep if not ready to read */
1629
                schedule_timeout_interruptible(1);
1630
#endif
1631
        }
1632
        printk(KERN_INFO "cosa%d: timeout in put_wait_data (status 0x%x)\n",
1633
                cosa->num, cosa_getstatus(cosa));
1634
        return -1;
1635
}
1636
 
1637
/*
1638
 * The following routine puts the hexadecimal number into the SRP monitor
1639
 * and verifies the proper echo of the sent bytes. Returns 0 on success,
1640
 * negative number on failure (-1,-3,-5,-7) means that put_wait_data() failed,
1641
 * (-2,-4,-6,-8) means that reading echo failed.
1642
 */
1643
static int puthexnumber(struct cosa_data *cosa, int number)
1644
{
1645
        char temp[5];
1646
        int i;
1647
 
1648
        /* Well, I should probably replace this by something faster. */
1649
        sprintf(temp, "%04X", number);
1650
        for (i=0; i<4; i++) {
1651
                if (put_wait_data(cosa, temp[i]) == -1) {
1652
                        printk(KERN_NOTICE "cosa%d: puthexnumber failed to write byte %d\n",
1653
                                cosa->num, i);
1654
                        return -1-2*i;
1655
                }
1656
                if (get_wait_data(cosa) != temp[i]) {
1657
                        printk(KERN_NOTICE "cosa%d: puthexhumber failed to read echo of byte %d\n",
1658
                                cosa->num, i);
1659
                        return -2-2*i;
1660
                }
1661
        }
1662
        return 0;
1663
}
1664
 
1665
 
1666
/* ---------- Interrupt routines ---------- */
1667
 
1668
/*
1669
 * There are three types of interrupt:
1670
 * At the beginning of transmit - this handled is in tx_interrupt(),
1671
 * at the beginning of receive - it is in rx_interrupt() and
1672
 * at the end of transmit/receive - it is the eot_interrupt() function.
1673
 * These functions are multiplexed by cosa_interrupt() according to the
1674
 * COSA status byte. I have moved the rx/tx/eot interrupt handling into
1675
 * separate functions to make it more readable. These functions are inline,
1676
 * so there should be no overhead of function call.
1677
 *
1678
 * In the COSA bus-master mode, we need to tell the card the address of a
1679
 * buffer. Unfortunately, COSA may be too slow for us, so we must busy-wait.
1680
 * It's time to use the bottom half :-(
1681
 */
1682
 
1683
/*
1684
 * Transmit interrupt routine - called when COSA is willing to obtain
1685
 * data from the OS. The most tricky part of the routine is selection
1686
 * of channel we (OS) want to send packet for. For SRP we should probably
1687
 * use the round-robin approach. The newer COSA firmwares have a simple
1688
 * flow-control - in the status word has bits 2 and 3 set to 1 means that the
1689
 * channel 0 or 1 doesn't want to receive data.
1690
 *
1691
 * It seems there is a bug in COSA firmware (need to trace it further):
1692
 * When the driver status says that the kernel has no more data for transmit
1693
 * (e.g. at the end of TX DMA) and then the kernel changes its mind
1694
 * (e.g. new packet is queued to hard_start_xmit()), the card issues
1695
 * the TX interrupt but does not mark the channel as ready-to-transmit.
1696
 * The fix seems to be to push the packet to COSA despite its request.
1697
 * We first try to obey the card's opinion, and then fall back to forced TX.
1698
 */
1699
static inline void tx_interrupt(struct cosa_data *cosa, int status)
1700
{
1701
        unsigned long flags, flags1;
1702
#ifdef DEBUG_IRQS
1703
        printk(KERN_INFO "cosa%d: SR_DOWN_REQUEST status=0x%04x\n",
1704
                cosa->num, status);
1705
#endif
1706
        spin_lock_irqsave(&cosa->lock, flags);
1707
        set_bit(TXBIT, &cosa->rxtx);
1708
        if (!test_bit(IRQBIT, &cosa->rxtx)) {
1709
                /* flow control, see the comment above */
1710
                int i=0;
1711
                if (!cosa->txbitmap) {
1712
                        printk(KERN_WARNING "%s: No channel wants data "
1713
                                "in TX IRQ. Expect DMA timeout.",
1714
                                cosa->name);
1715
                        put_driver_status_nolock(cosa);
1716
                        clear_bit(TXBIT, &cosa->rxtx);
1717
                        spin_unlock_irqrestore(&cosa->lock, flags);
1718
                        return;
1719
                }
1720
                while(1) {
1721
                        cosa->txchan++;
1722
                        i++;
1723
                        if (cosa->txchan >= cosa->nchannels)
1724
                                cosa->txchan = 0;
1725
                        if (!(cosa->txbitmap & (1<<cosa->txchan)))
1726
                                continue;
1727
                        if (~status & (1 << (cosa->txchan+DRIVER_TXMAP_SHIFT)))
1728
                                break;
1729
                        /* in second pass, accept first ready-to-TX channel */
1730
                        if (i > cosa->nchannels) {
1731
                                /* Can be safely ignored */
1732
#ifdef DEBUG_IRQS
1733
                                printk(KERN_DEBUG "%s: Forcing TX "
1734
                                        "to not-ready channel %d\n",
1735
                                        cosa->name, cosa->txchan);
1736
#endif
1737
                                break;
1738
                        }
1739
                }
1740
 
1741
                cosa->txsize = cosa->chan[cosa->txchan].txsize;
1742
                if (cosa_dma_able(cosa->chan+cosa->txchan,
1743
                        cosa->chan[cosa->txchan].txbuf, cosa->txsize)) {
1744
                        cosa->txbuf = cosa->chan[cosa->txchan].txbuf;
1745
                } else {
1746
                        memcpy(cosa->bouncebuf, cosa->chan[cosa->txchan].txbuf,
1747
                                cosa->txsize);
1748
                        cosa->txbuf = cosa->bouncebuf;
1749
                }
1750
        }
1751
 
1752
        if (is_8bit(cosa)) {
1753
                if (!test_bit(IRQBIT, &cosa->rxtx)) {
1754
                        cosa_putstatus(cosa, SR_TX_INT_ENA);
1755
                        cosa_putdata8(cosa, ((cosa->txchan << 5) & 0xe0)|
1756
                                ((cosa->txsize >> 8) & 0x1f));
1757
#ifdef DEBUG_IO
1758
                        debug_status_out(cosa, SR_TX_INT_ENA);
1759
                        debug_data_out(cosa, ((cosa->txchan << 5) & 0xe0)|
1760
                                ((cosa->txsize >> 8) & 0x1f));
1761
                        debug_data_in(cosa, cosa_getdata8(cosa));
1762
#else
1763
                        cosa_getdata8(cosa);
1764
#endif
1765
                        set_bit(IRQBIT, &cosa->rxtx);
1766
                        spin_unlock_irqrestore(&cosa->lock, flags);
1767
                        return;
1768
                } else {
1769
                        clear_bit(IRQBIT, &cosa->rxtx);
1770
                        cosa_putstatus(cosa, 0);
1771
                        cosa_putdata8(cosa, cosa->txsize&0xff);
1772
#ifdef DEBUG_IO
1773
                        debug_status_out(cosa, 0);
1774
                        debug_data_out(cosa, cosa->txsize&0xff);
1775
#endif
1776
                }
1777
        } else {
1778
                cosa_putstatus(cosa, SR_TX_INT_ENA);
1779
                cosa_putdata16(cosa, ((cosa->txchan<<13) & 0xe000)
1780
                        | (cosa->txsize & 0x1fff));
1781
#ifdef DEBUG_IO
1782
                debug_status_out(cosa, SR_TX_INT_ENA);
1783
                debug_data_out(cosa, ((cosa->txchan<<13) & 0xe000)
1784
                        | (cosa->txsize & 0x1fff));
1785
                debug_data_in(cosa, cosa_getdata8(cosa));
1786
                debug_status_out(cosa, 0);
1787
#else
1788
                cosa_getdata8(cosa);
1789
#endif
1790
                cosa_putstatus(cosa, 0);
1791
        }
1792
 
1793
        if (cosa->busmaster) {
1794
                unsigned long addr = virt_to_bus(cosa->txbuf);
1795
                int count=0;
1796
                printk(KERN_INFO "busmaster IRQ\n");
1797
                while (!(cosa_getstatus(cosa)&SR_TX_RDY)) {
1798
                        count++;
1799
                        udelay(10);
1800
                        if (count > 1000) break;
1801
                }
1802
                printk(KERN_INFO "status %x\n", cosa_getstatus(cosa));
1803
                printk(KERN_INFO "ready after %d loops\n", count);
1804
                cosa_putdata16(cosa, (addr >> 16)&0xffff);
1805
 
1806
                count = 0;
1807
                while (!(cosa_getstatus(cosa)&SR_TX_RDY)) {
1808
                        count++;
1809
                        if (count > 1000) break;
1810
                        udelay(10);
1811
                }
1812
                printk(KERN_INFO "ready after %d loops\n", count);
1813
                cosa_putdata16(cosa, addr &0xffff);
1814
                flags1 = claim_dma_lock();
1815
                set_dma_mode(cosa->dma, DMA_MODE_CASCADE);
1816
                enable_dma(cosa->dma);
1817
                release_dma_lock(flags1);
1818
        } else {
1819
                /* start the DMA */
1820
                flags1 = claim_dma_lock();
1821
                disable_dma(cosa->dma);
1822
                clear_dma_ff(cosa->dma);
1823
                set_dma_mode(cosa->dma, DMA_MODE_WRITE);
1824
                set_dma_addr(cosa->dma, virt_to_bus(cosa->txbuf));
1825
                set_dma_count(cosa->dma, cosa->txsize);
1826
                enable_dma(cosa->dma);
1827
                release_dma_lock(flags1);
1828
        }
1829
        cosa_putstatus(cosa, SR_TX_DMA_ENA|SR_USR_INT_ENA);
1830
#ifdef DEBUG_IO
1831
        debug_status_out(cosa, SR_TX_DMA_ENA|SR_USR_INT_ENA);
1832
#endif
1833
        spin_unlock_irqrestore(&cosa->lock, flags);
1834
}
1835
 
1836
static inline void rx_interrupt(struct cosa_data *cosa, int status)
1837
{
1838
        unsigned long flags;
1839
#ifdef DEBUG_IRQS
1840
        printk(KERN_INFO "cosa%d: SR_UP_REQUEST\n", cosa->num);
1841
#endif
1842
 
1843
        spin_lock_irqsave(&cosa->lock, flags);
1844
        set_bit(RXBIT, &cosa->rxtx);
1845
 
1846
        if (is_8bit(cosa)) {
1847
                if (!test_bit(IRQBIT, &cosa->rxtx)) {
1848
                        set_bit(IRQBIT, &cosa->rxtx);
1849
                        put_driver_status_nolock(cosa);
1850
                        cosa->rxsize = cosa_getdata8(cosa) <<8;
1851
#ifdef DEBUG_IO
1852
                        debug_data_in(cosa, cosa->rxsize >> 8);
1853
#endif
1854
                        spin_unlock_irqrestore(&cosa->lock, flags);
1855
                        return;
1856
                } else {
1857
                        clear_bit(IRQBIT, &cosa->rxtx);
1858
                        cosa->rxsize |= cosa_getdata8(cosa) & 0xff;
1859
#ifdef DEBUG_IO
1860
                        debug_data_in(cosa, cosa->rxsize & 0xff);
1861
#endif
1862
#if 0
1863
                        printk(KERN_INFO "cosa%d: receive rxsize = (0x%04x).\n",
1864
                                cosa->num, cosa->rxsize);
1865
#endif
1866
                }
1867
        } else {
1868
                cosa->rxsize = cosa_getdata16(cosa);
1869
#ifdef DEBUG_IO
1870
                debug_data_in(cosa, cosa->rxsize);
1871
#endif
1872
#if 0
1873
                printk(KERN_INFO "cosa%d: receive rxsize = (0x%04x).\n",
1874
                        cosa->num, cosa->rxsize);
1875
#endif
1876
        }
1877
        if (((cosa->rxsize & 0xe000) >> 13) >= cosa->nchannels) {
1878
                printk(KERN_WARNING "%s: rx for unknown channel (0x%04x)\n",
1879
                        cosa->name, cosa->rxsize);
1880
                spin_unlock_irqrestore(&cosa->lock, flags);
1881
                goto reject;
1882
        }
1883
        cosa->rxchan = cosa->chan + ((cosa->rxsize & 0xe000) >> 13);
1884
        cosa->rxsize &= 0x1fff;
1885
        spin_unlock_irqrestore(&cosa->lock, flags);
1886
 
1887
        cosa->rxbuf = NULL;
1888
        if (cosa->rxchan->setup_rx)
1889
                cosa->rxbuf = cosa->rxchan->setup_rx(cosa->rxchan, cosa->rxsize);
1890
 
1891
        if (!cosa->rxbuf) {
1892
reject:         /* Reject the packet */
1893
                printk(KERN_INFO "cosa%d: rejecting packet on channel %d\n",
1894
                        cosa->num, cosa->rxchan->num);
1895
                cosa->rxbuf = cosa->bouncebuf;
1896
        }
1897
 
1898
        /* start the DMA */
1899
        flags = claim_dma_lock();
1900
        disable_dma(cosa->dma);
1901
        clear_dma_ff(cosa->dma);
1902
        set_dma_mode(cosa->dma, DMA_MODE_READ);
1903
        if (cosa_dma_able(cosa->rxchan, cosa->rxbuf, cosa->rxsize & 0x1fff)) {
1904
                set_dma_addr(cosa->dma, virt_to_bus(cosa->rxbuf));
1905
        } else {
1906
                set_dma_addr(cosa->dma, virt_to_bus(cosa->bouncebuf));
1907
        }
1908
        set_dma_count(cosa->dma, (cosa->rxsize&0x1fff));
1909
        enable_dma(cosa->dma);
1910
        release_dma_lock(flags);
1911
        spin_lock_irqsave(&cosa->lock, flags);
1912
        cosa_putstatus(cosa, SR_RX_DMA_ENA|SR_USR_INT_ENA);
1913
        if (!is_8bit(cosa) && (status & SR_TX_RDY))
1914
                cosa_putdata8(cosa, DRIVER_RX_READY);
1915
#ifdef DEBUG_IO
1916
        debug_status_out(cosa, SR_RX_DMA_ENA|SR_USR_INT_ENA);
1917
        if (!is_8bit(cosa) && (status & SR_TX_RDY))
1918
                debug_data_cmd(cosa, DRIVER_RX_READY);
1919
#endif
1920
        spin_unlock_irqrestore(&cosa->lock, flags);
1921
}
1922
 
1923
static inline void eot_interrupt(struct cosa_data *cosa, int status)
1924
{
1925
        unsigned long flags, flags1;
1926
        spin_lock_irqsave(&cosa->lock, flags);
1927
        flags1 = claim_dma_lock();
1928
        disable_dma(cosa->dma);
1929
        clear_dma_ff(cosa->dma);
1930
        release_dma_lock(flags1);
1931
        if (test_bit(TXBIT, &cosa->rxtx)) {
1932
                struct channel_data *chan = cosa->chan+cosa->txchan;
1933
                if (chan->tx_done)
1934
                        if (chan->tx_done(chan, cosa->txsize))
1935
                                clear_bit(chan->num, &cosa->txbitmap);
1936
        } else if (test_bit(RXBIT, &cosa->rxtx)) {
1937
#ifdef DEBUG_DATA
1938
        {
1939
                int i;
1940
                printk(KERN_INFO "cosa%dc%d: done rx(0x%x)", cosa->num,
1941
                        cosa->rxchan->num, cosa->rxsize);
1942
                for (i=0; i<cosa->rxsize; i++)
1943
                        printk (" %02x", cosa->rxbuf[i]&0xff);
1944
                printk("\n");
1945
        }
1946
#endif
1947
                /* Packet for unknown channel? */
1948
                if (cosa->rxbuf == cosa->bouncebuf)
1949
                        goto out;
1950
                if (!cosa_dma_able(cosa->rxchan, cosa->rxbuf, cosa->rxsize))
1951
                        memcpy(cosa->rxbuf, cosa->bouncebuf, cosa->rxsize);
1952
                if (cosa->rxchan->rx_done)
1953
                        if (cosa->rxchan->rx_done(cosa->rxchan))
1954
                                clear_bit(cosa->rxchan->num, &cosa->rxbitmap);
1955
        } else {
1956
                printk(KERN_NOTICE "cosa%d: unexpected EOT interrupt\n",
1957
                        cosa->num);
1958
        }
1959
        /*
1960
         * Clear the RXBIT, TXBIT and IRQBIT (the latest should be
1961
         * cleared anyway). We should do it as soon as possible
1962
         * so that we can tell the COSA we are done and to give it a time
1963
         * for recovery.
1964
         */
1965
out:
1966
        cosa->rxtx = 0;
1967
        put_driver_status_nolock(cosa);
1968
        spin_unlock_irqrestore(&cosa->lock, flags);
1969
}
1970
 
1971
static irqreturn_t cosa_interrupt(int irq, void *cosa_)
1972
{
1973
        unsigned status;
1974
        int count = 0;
1975
        struct cosa_data *cosa = cosa_;
1976
again:
1977
        status = cosa_getstatus(cosa);
1978
#ifdef DEBUG_IRQS
1979
        printk(KERN_INFO "cosa%d: got IRQ, status 0x%02x\n", cosa->num,
1980
                status & 0xff);
1981
#endif
1982
#ifdef DEBUG_IO
1983
        debug_status_in(cosa, status);
1984
#endif
1985
        switch (status & SR_CMD_FROM_SRP_MASK) {
1986
        case SR_DOWN_REQUEST:
1987
                tx_interrupt(cosa, status);
1988
                break;
1989
        case SR_UP_REQUEST:
1990
                rx_interrupt(cosa, status);
1991
                break;
1992
        case SR_END_OF_TRANSFER:
1993
                eot_interrupt(cosa, status);
1994
                break;
1995
        default:
1996
                /* We may be too fast for SRP. Try to wait a bit more. */
1997
                if (count++ < 100) {
1998
                        udelay(100);
1999
                        goto again;
2000
                }
2001
                printk(KERN_INFO "cosa%d: unknown status 0x%02x in IRQ after %d retries\n",
2002
                        cosa->num, status & 0xff, count);
2003
        }
2004
#ifdef DEBUG_IRQS
2005
        if (count)
2006
                printk(KERN_INFO "%s: %d-times got unknown status in IRQ\n",
2007
                        cosa->name, count);
2008
        else
2009
                printk(KERN_INFO "%s: returning from IRQ\n", cosa->name);
2010
#endif
2011
        return IRQ_HANDLED;
2012
}
2013
 
2014
 
2015
/* ---------- I/O debugging routines ---------- */
2016
/*
2017
 * These routines can be used to monitor COSA/SRP I/O and to printk()
2018
 * the data being transferred on the data and status I/O port in a
2019
 * readable way.
2020
 */
2021
 
2022
#ifdef DEBUG_IO
2023
static void debug_status_in(struct cosa_data *cosa, int status)
2024
{
2025
        char *s;
2026
        switch(status & SR_CMD_FROM_SRP_MASK) {
2027
        case SR_UP_REQUEST:
2028
                s = "RX_REQ";
2029
                break;
2030
        case SR_DOWN_REQUEST:
2031
                s = "TX_REQ";
2032
                break;
2033
        case SR_END_OF_TRANSFER:
2034
                s = "ET_REQ";
2035
                break;
2036
        default:
2037
                s = "NO_REQ";
2038
                break;
2039
        }
2040
        printk(KERN_INFO "%s: IO: status -> 0x%02x (%s%s%s%s)\n",
2041
                cosa->name,
2042
                status,
2043
                status & SR_USR_RQ ? "USR_RQ|":"",
2044
                status & SR_TX_RDY ? "TX_RDY|":"",
2045
                status & SR_RX_RDY ? "RX_RDY|":"",
2046
                s);
2047
}
2048
 
2049
static void debug_status_out(struct cosa_data *cosa, int status)
2050
{
2051
        printk(KERN_INFO "%s: IO: status <- 0x%02x (%s%s%s%s%s%s)\n",
2052
                cosa->name,
2053
                status,
2054
                status & SR_RX_DMA_ENA  ? "RXDMA|":"!rxdma|",
2055
                status & SR_TX_DMA_ENA  ? "TXDMA|":"!txdma|",
2056
                status & SR_RST         ? "RESET|":"",
2057
                status & SR_USR_INT_ENA ? "USRINT|":"!usrint|",
2058
                status & SR_TX_INT_ENA  ? "TXINT|":"!txint|",
2059
                status & SR_RX_INT_ENA  ? "RXINT":"!rxint");
2060
}
2061
 
2062
static void debug_data_in(struct cosa_data *cosa, int data)
2063
{
2064
        printk(KERN_INFO "%s: IO: data -> 0x%04x\n", cosa->name, data);
2065
}
2066
 
2067
static void debug_data_out(struct cosa_data *cosa, int data)
2068
{
2069
        printk(KERN_INFO "%s: IO: data <- 0x%04x\n", cosa->name, data);
2070
}
2071
 
2072
static void debug_data_cmd(struct cosa_data *cosa, int data)
2073
{
2074
        printk(KERN_INFO "%s: IO: data <- 0x%04x (%s|%s)\n",
2075
                cosa->name, data,
2076
                data & SR_RDY_RCV ? "RX_RDY" : "!rx_rdy",
2077
                data & SR_RDY_SND ? "TX_RDY" : "!tx_rdy");
2078
}
2079
#endif
2080
 
2081
/* EOF -- this file has not been truncated */

powered by: WebSVN 2.1.0

© copyright 1999-2025 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.