Add the rt linux 4.1.3-rt3 as base
[kvmfornfv.git] / kernel / drivers / staging / ft1000 / ft1000-pcmcia / ft1000_hw.c
1 /*---------------------------------------------------------------------------
2   FT1000 driver for Flarion Flash OFDM NIC Device
3
4   Copyright (C) 2002 Flarion Technologies, All rights reserved.
5   Copyright (C) 2006 Patrik Ostrihon, All rights reserved.
6   Copyright (C) 2006 ProWeb Consulting, a.s, All rights reserved.
7
8   This program is free software; you can redistribute it and/or modify it
9   under the terms of the GNU General Public License as published by the Free
10   Software Foundation; either version 2 of the License, or (at your option) any
11   later version. This program is distributed in the hope that it will be useful,
12   but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
13   or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14   more details. You should have received a copy of the GNU General Public
15   License along with this program; if not, write to the
16   Free Software Foundation, Inc., 59 Temple Place -
17   Suite 330, Boston, MA 02111-1307, USA.
18   -------------------------------------------------------------------------*/
19
20 #define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
21
22 #include <linux/kernel.h>
23 #include <linux/module.h>
24 #include <linux/sched.h>
25 #include <linux/ptrace.h>
26 #include <linux/slab.h>
27 #include <linux/string.h>
28 #include <linux/timer.h>
29 #include <linux/interrupt.h>
30 #include <linux/in.h>
31 #include <linux/io.h>
32 #include <linux/bitops.h>
33
34 #include <linux/netdevice.h>
35 #include <linux/etherdevice.h>
36 #include <linux/skbuff.h>
37 #include <linux/if_arp.h>
38 #include <linux/ioport.h>
39 #include <linux/wait.h>
40 #include <linux/vmalloc.h>
41
42 #include <linux/firmware.h>
43 #include <linux/ethtool.h>
44
45 #include <pcmcia/cistpl.h>
46 #include <pcmcia/cisreg.h>
47 #include <pcmcia/ds.h>
48
49 #include <linux/delay.h>
50 #include "ft1000.h"
51
52 static const struct firmware *fw_entry;
53
54 static void ft1000_hbchk(u_long data);
55 static struct timer_list poll_timer = {
56         .function = ft1000_hbchk
57 };
58
59 static u16 cmdbuffer[1024];
60 static u8 tempbuffer[1600];
61 static u8 ft1000_card_present;
62 static u8 flarion_ft1000_cnt;
63
64 static irqreturn_t ft1000_interrupt(int irq, void *dev_id);
65 static void ft1000_enable_interrupts(struct net_device *dev);
66 static void ft1000_disable_interrupts(struct net_device *dev);
67
68 /* new kernel */
69 MODULE_AUTHOR("");
70 MODULE_DESCRIPTION("Support for Flarion Flash OFDM NIC Device. Support for PCMCIA when used with ft1000_cs.");
71 MODULE_LICENSE("GPL");
72 MODULE_SUPPORTED_DEVICE("FT1000");
73
74 #define MAX_RCV_LOOP   100
75
76 /*---------------------------------------------------------------------------
77
78   Function:   ft1000_read_fifo_len
79   Description: This function will read the ASIC Uplink FIFO status register
80   which will return the number of bytes remaining in the Uplink FIFO.
81   Sixteen bytes are subtracted to make sure that the ASIC does not
82   reach its threshold.
83   Input:
84   dev    - network device structure
85   Output:
86   value  - number of bytes available in the ASIC Uplink FIFO.
87
88   -------------------------------------------------------------------------*/
89 static inline u16 ft1000_read_fifo_len(struct net_device *dev)
90 {
91         struct ft1000_info *info = netdev_priv(dev);
92
93         if (info->AsicID == ELECTRABUZZ_ID)
94                 return (ft1000_read_reg(dev, FT1000_REG_UFIFO_STAT) - 16);
95         else
96                 return (ft1000_read_reg(dev, FT1000_REG_MAG_UFSR) - 16);
97 }
98
99 /*---------------------------------------------------------------------------
100
101   Function:   ft1000_read_dpram
102   Description: This function will read the specific area of dpram
103   (Electrabuzz ASIC only)
104   Input:
105   dev    - device structure
106   offset - index of dpram
107   Output:
108   value  - value of dpram
109
110   -------------------------------------------------------------------------*/
111 u16 ft1000_read_dpram(struct net_device *dev, int offset)
112 {
113         struct ft1000_info *info = netdev_priv(dev);
114         unsigned long flags;
115         u16 data;
116
117         /* Provide mutual exclusive access while reading ASIC registers. */
118         spin_lock_irqsave(&info->dpram_lock, flags);
119         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset);
120         data = ft1000_read_reg(dev, FT1000_REG_DPRAM_DATA);
121         spin_unlock_irqrestore(&info->dpram_lock, flags);
122
123         return data;
124 }
125
126 /*---------------------------------------------------------------------------
127
128   Function:   ft1000_write_dpram
129   Description: This function will write to a specific area of dpram
130   (Electrabuzz ASIC only)
131   Input:
132   dev    - device structure
133   offset - index of dpram
134   value  - value to write
135   Output:
136   none.
137
138   -------------------------------------------------------------------------*/
139 static inline void ft1000_write_dpram(struct net_device *dev,
140                                       int offset, u16 value)
141 {
142         struct ft1000_info *info = netdev_priv(dev);
143         unsigned long flags;
144
145         /* Provide mutual exclusive access while reading ASIC registers. */
146         spin_lock_irqsave(&info->dpram_lock, flags);
147         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset);
148         ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, value);
149         spin_unlock_irqrestore(&info->dpram_lock, flags);
150 }
151
152 /*---------------------------------------------------------------------------
153
154   Function:   ft1000_read_dpram_mag_16
155   Description: This function will read the specific area of dpram
156   (Magnemite ASIC only)
157   Input:
158   dev    - device structure
159   offset - index of dpram
160   Output:
161   value  - value of dpram
162
163   -------------------------------------------------------------------------*/
164 u16 ft1000_read_dpram_mag_16(struct net_device *dev, int offset, int Index)
165 {
166         struct ft1000_info *info = netdev_priv(dev);
167         unsigned long flags;
168         u16 data;
169
170         /* Provide mutual exclusive access while reading ASIC registers. */
171         spin_lock_irqsave(&info->dpram_lock, flags);
172         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset);
173         /* check if we want to read upper or lower 32-bit word */
174         if (Index)
175                 data = ft1000_read_reg(dev, FT1000_REG_MAG_DPDATAL);
176         else
177                 data = ft1000_read_reg(dev, FT1000_REG_MAG_DPDATAH);
178
179         spin_unlock_irqrestore(&info->dpram_lock, flags);
180
181         return data;
182 }
183
184 /*---------------------------------------------------------------------------
185
186   Function:   ft1000_write_dpram_mag_16
187   Description: This function will write to a specific area of dpram
188   (Magnemite ASIC only)
189   Input:
190   dev    - device structure
191   offset - index of dpram
192   value  - value to write
193   Output:
194   none.
195
196   -------------------------------------------------------------------------*/
197 static inline void ft1000_write_dpram_mag_16(struct net_device *dev,
198                                              int offset, u16 value, int Index)
199 {
200         struct ft1000_info *info = netdev_priv(dev);
201         unsigned long flags;
202
203         /* Provide mutual exclusive access while reading ASIC registers. */
204         spin_lock_irqsave(&info->dpram_lock, flags);
205         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset);
206         if (Index)
207                 ft1000_write_reg(dev, FT1000_REG_MAG_DPDATAL, value);
208         else
209                 ft1000_write_reg(dev, FT1000_REG_MAG_DPDATAH, value);
210
211         spin_unlock_irqrestore(&info->dpram_lock, flags);
212 }
213
214 /*---------------------------------------------------------------------------
215
216   Function:   ft1000_read_dpram_mag_32
217   Description: This function will read the specific area of dpram
218   (Magnemite ASIC only)
219   Input:
220   dev    - device structure
221   offset - index of dpram
222   Output:
223   value  - value of dpram
224
225   -------------------------------------------------------------------------*/
226 u32 ft1000_read_dpram_mag_32(struct net_device *dev, int offset)
227 {
228         struct ft1000_info *info = netdev_priv(dev);
229         unsigned long flags;
230         u32 data;
231
232         /* Provide mutual exclusive access while reading ASIC registers. */
233         spin_lock_irqsave(&info->dpram_lock, flags);
234         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset);
235         data = inl(dev->base_addr + FT1000_REG_MAG_DPDATAL);
236         spin_unlock_irqrestore(&info->dpram_lock, flags);
237
238         return data;
239 }
240
241 /*---------------------------------------------------------------------------
242
243   Function:   ft1000_write_dpram_mag_32
244   Description: This function will write to a specific area of dpram
245   (Magnemite ASIC only)
246   Input:
247   dev    - device structure
248   offset - index of dpram
249   value  - value to write
250   Output:
251   none.
252
253   -------------------------------------------------------------------------*/
254 void ft1000_write_dpram_mag_32(struct net_device *dev, int offset, u32 value)
255 {
256         struct ft1000_info *info = netdev_priv(dev);
257         unsigned long flags;
258
259         /* Provide mutual exclusive access while reading ASIC registers. */
260         spin_lock_irqsave(&info->dpram_lock, flags);
261         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, offset);
262         outl(value, dev->base_addr + FT1000_REG_MAG_DPDATAL);
263         spin_unlock_irqrestore(&info->dpram_lock, flags);
264 }
265
266 /*---------------------------------------------------------------------------
267
268   Function:   ft1000_enable_interrupts
269   Description: This function will enable interrupts base on the current
270                interrupt mask.
271   Input:
272   dev    - device structure
273   Output:
274   None.
275
276   -------------------------------------------------------------------------*/
277 static void ft1000_enable_interrupts(struct net_device *dev)
278 {
279         u16 tempword;
280
281         ft1000_write_reg(dev, FT1000_REG_SUP_IMASK, ISR_DEFAULT_MASK);
282         tempword = ft1000_read_reg(dev, FT1000_REG_SUP_IMASK);
283         pr_debug("current interrupt enable mask = 0x%x\n", tempword);
284 }
285
286 /*---------------------------------------------------------------------------
287
288   Function:   ft1000_disable_interrupts
289   Description: This function will disable all interrupts.
290   Input:
291   dev    - device structure
292   Output:
293   None.
294
295   -------------------------------------------------------------------------*/
296 static void ft1000_disable_interrupts(struct net_device *dev)
297 {
298         u16 tempword;
299
300         ft1000_write_reg(dev, FT1000_REG_SUP_IMASK, ISR_MASK_ALL);
301         tempword = ft1000_read_reg(dev, FT1000_REG_SUP_IMASK);
302         pr_debug("current interrupt enable mask = 0x%x\n", tempword);
303 }
304
305 /*---------------------------------------------------------------------------
306   Function:     ft1000_read_dsp_timer
307   Description:  This function reads the DSP timer and stores its value in the
308                 DSP_TIME field of the ft1000_info struct passed as argument
309   Input:
310   dev    - device structure
311   info   - ft1000_info structure
312   Output:
313   None.
314
315   -------------------------------------------------------------------------*/
316 static void ft1000_read_dsp_timer(struct net_device *dev,
317                                   struct ft1000_info *info)
318 {
319         if (info->AsicID == ELECTRABUZZ_ID) {
320                 info->DSP_TIME[0] = ft1000_read_dpram(dev, FT1000_DSP_TIMER0);
321                 info->DSP_TIME[1] = ft1000_read_dpram(dev, FT1000_DSP_TIMER1);
322                 info->DSP_TIME[2] = ft1000_read_dpram(dev, FT1000_DSP_TIMER2);
323                 info->DSP_TIME[3] = ft1000_read_dpram(dev, FT1000_DSP_TIMER3);
324         } else {
325                 info->DSP_TIME[0] =
326                         ft1000_read_dpram_mag_16(dev, FT1000_MAG_DSP_TIMER0,
327                                                  FT1000_MAG_DSP_TIMER0_INDX);
328                 info->DSP_TIME[1] =
329                         ft1000_read_dpram_mag_16(dev, FT1000_MAG_DSP_TIMER1,
330                                                  FT1000_MAG_DSP_TIMER1_INDX);
331                 info->DSP_TIME[2] =
332                         ft1000_read_dpram_mag_16(dev, FT1000_MAG_DSP_TIMER2,
333                                                  FT1000_MAG_DSP_TIMER2_INDX);
334                 info->DSP_TIME[3] =
335                         ft1000_read_dpram_mag_16(dev, FT1000_MAG_DSP_TIMER3,
336                                                  FT1000_MAG_DSP_TIMER3_INDX);
337         }
338 }
339
340 /*---------------------------------------------------------------------------
341
342   Function:   ft1000_reset_asic
343   Description: This function will call the Card Service function to reset the
344   ASIC.
345   Input:
346   dev    - device structure
347   Output:
348   none
349
350   -------------------------------------------------------------------------*/
351 static void ft1000_reset_asic(struct net_device *dev)
352 {
353         struct ft1000_info *info = netdev_priv(dev);
354         struct ft1000_pcmcia *pcmcia = info->priv;
355         u16 tempword;
356
357         (*info->ft1000_reset) (pcmcia->link);
358
359         /*
360          * Let's use the register provided by the Magnemite ASIC to reset the
361          * ASIC and DSP.
362          */
363         if (info->AsicID == MAGNEMITE_ID) {
364                 ft1000_write_reg(dev, FT1000_REG_RESET,
365                                  DSP_RESET_BIT | ASIC_RESET_BIT);
366         }
367         mdelay(1);
368         if (info->AsicID == ELECTRABUZZ_ID) {
369                 /* set watermark to -1 in order to not generate an interrupt */
370                 ft1000_write_reg(dev, FT1000_REG_WATERMARK, 0xffff);
371         } else {
372                 /* set watermark to -1 in order to not generate an interrupt */
373                 ft1000_write_reg(dev, FT1000_REG_MAG_WATERMARK, 0xffff);
374         }
375         /* clear interrupts */
376         tempword = ft1000_read_reg(dev, FT1000_REG_SUP_ISR);
377         pr_debug("interrupt status register = 0x%x\n", tempword);
378         ft1000_write_reg(dev, FT1000_REG_SUP_ISR, tempword);
379         tempword = ft1000_read_reg(dev, FT1000_REG_SUP_ISR);
380         pr_debug("interrupt status register = 0x%x\n", tempword);
381
382 }
383
384 /*---------------------------------------------------------------------------
385
386   Function:   ft1000_reset_card
387   Description: This function will reset the card
388   Input:
389   dev    - device structure
390   Output:
391   status - false (card reset fail)
392   true  (card reset successful)
393
394   -------------------------------------------------------------------------*/
395 static int ft1000_reset_card(struct net_device *dev)
396 {
397         struct ft1000_info *info = netdev_priv(dev);
398         u16 tempword;
399         int i;
400         unsigned long flags;
401         struct prov_record *ptr;
402         struct prov_record *tmp;
403
404         info->CardReady = 0;
405         info->ProgConStat = 0;
406         info->squeseqnum = 0;
407         ft1000_disable_interrupts(dev);
408
409         /* del_timer(&poll_timer); */
410
411         /* Make sure we free any memory reserve for provisioning */
412         list_for_each_entry_safe(ptr, tmp, &info->prov_list, list) {
413                 pr_debug("deleting provisioning record\n");
414                 list_del(&ptr->list);
415                 kfree(ptr->pprov_data);
416                 kfree(ptr);
417         }
418
419         if (info->AsicID == ELECTRABUZZ_ID) {
420                 pr_debug("resetting DSP\n");
421                 ft1000_write_reg(dev, FT1000_REG_RESET, DSP_RESET_BIT);
422         } else {
423                 pr_debug("resetting ASIC and DSP\n");
424                 ft1000_write_reg(dev, FT1000_REG_RESET,
425                                  DSP_RESET_BIT | ASIC_RESET_BIT);
426         }
427
428         /* Copy DSP session record into info block if this is not a coldstart */
429         if (ft1000_card_present == 1) {
430                 spin_lock_irqsave(&info->dpram_lock, flags);
431                 if (info->AsicID == ELECTRABUZZ_ID) {
432                         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
433                                          FT1000_DPRAM_RX_BASE);
434                         for (i = 0; i < MAX_DSP_SESS_REC; i++) {
435                                 info->DSPSess.Rec[i] =
436                                         ft1000_read_reg(dev,
437                                                         FT1000_REG_DPRAM_DATA);
438                         }
439                 } else {
440                         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
441                                          FT1000_DPRAM_MAG_RX_BASE);
442                         for (i = 0; i < MAX_DSP_SESS_REC / 2; i++) {
443                                 info->DSPSess.MagRec[i] =
444                                         inl(dev->base_addr
445                                                 + FT1000_REG_MAG_DPDATA);
446                         }
447                 }
448                 spin_unlock_irqrestore(&info->dpram_lock, flags);
449         }
450
451         pr_debug("resetting ASIC\n");
452         mdelay(10);
453         /* reset ASIC */
454         ft1000_reset_asic(dev);
455
456         pr_debug("downloading dsp image\n");
457
458         if (info->AsicID == MAGNEMITE_ID) {
459                 /* Put dsp in reset and take ASIC out of reset */
460                 pr_debug("Put DSP in reset and take ASIC out of reset\n");
461                 ft1000_write_reg(dev, FT1000_REG_RESET, DSP_RESET_BIT);
462
463                 /* Setting MAGNEMITE ASIC to big endian mode */
464                 ft1000_write_reg(dev, FT1000_REG_SUP_CTRL, HOST_INTF_BE);
465                 /* Download bootloader */
466                 card_bootload(dev);
467
468                 /* Take DSP out of reset */
469                 ft1000_write_reg(dev, FT1000_REG_RESET, 0);
470                 /* FLARION_DSP_ACTIVE; */
471                 mdelay(10);
472                 pr_debug("Take DSP out of reset\n");
473
474                 /*
475                  * Wait for 0xfefe indicating dsp ready before starting
476                  * download
477                  */
478                 for (i = 0; i < 50; i++) {
479                         tempword = ft1000_read_dpram_mag_16(dev,
480                                                 FT1000_MAG_DPRAM_FEFE,
481                                                 FT1000_MAG_DPRAM_FEFE_INDX);
482                         if (tempword == 0xfefe)
483                                 break;
484                         mdelay(20);
485                 }
486
487                 if (i == 50) {
488                         pr_debug("No FEFE detected from DSP\n");
489                         return false;
490                 }
491
492         } else {
493                 /* Take DSP out of reset */
494                 ft1000_write_reg(dev, FT1000_REG_RESET, ~DSP_RESET_BIT);
495                 mdelay(10);
496         }
497
498         if (card_download(dev, fw_entry->data, fw_entry->size)) {
499                 pr_debug("card download unsuccessful\n");
500                 return false;
501         }
502         pr_debug("card download successful\n");
503
504         mdelay(10);
505
506         if (info->AsicID == ELECTRABUZZ_ID) {
507                 /*
508                  * Need to initialize the FIFO length counter to zero in order
509                  * to sync up with the DSP
510                  */
511                 info->fifo_cnt = 0;
512                 ft1000_write_dpram(dev, FT1000_FIFO_LEN, info->fifo_cnt);
513                 /* Initialize DSP heartbeat area to ho */
514                 ft1000_write_dpram(dev, FT1000_HI_HO, ho);
515                 tempword = ft1000_read_dpram(dev, FT1000_HI_HO);
516                 pr_debug("hi_ho value = 0x%x\n", tempword);
517         } else {
518                 /* Initialize DSP heartbeat area to ho */
519                 ft1000_write_dpram_mag_16(dev, FT1000_MAG_HI_HO, ho_mag,
520                                           FT1000_MAG_HI_HO_INDX);
521                 tempword =
522                         ft1000_read_dpram_mag_16(dev, FT1000_MAG_HI_HO,
523                                                  FT1000_MAG_HI_HO_INDX);
524                 pr_debug("hi_ho value = 0x%x\n", tempword);
525         }
526
527         info->CardReady = 1;
528         ft1000_enable_interrupts(dev);
529
530         /* Schedule heartbeat process to run every 2 seconds */
531         /* poll_timer.expires = jiffies + (2*HZ); */
532         /* poll_timer.data = (u_long)dev; */
533         /* add_timer(&poll_timer); */
534
535         return true;
536
537 }
538
539 /*---------------------------------------------------------------------------
540
541   Function:   ft1000_chkcard
542   Description: This function will check if the device is presently available on
543   the system.
544   Input:
545   dev    - device structure
546   Output:
547   status - false (device is not present)
548   true  (device is present)
549
550   -------------------------------------------------------------------------*/
551 static int ft1000_chkcard(struct net_device *dev)
552 {
553         u16 tempword;
554
555         /*
556          * Mask register is used to check for device presence since it is never
557          * set to zero.
558          */
559         tempword = ft1000_read_reg(dev, FT1000_REG_SUP_IMASK);
560         if (tempword == 0) {
561                 pr_debug("IMASK = 0 Card not detected\n");
562                 return false;
563         }
564         /*
565          * The system will return the value of 0xffff for the version register
566          * if the device is not present.
567          */
568         tempword = ft1000_read_reg(dev, FT1000_REG_ASIC_ID);
569         if (tempword == 0xffff) {
570                 pr_debug("Version = 0xffff Card not detected\n");
571                 return false;
572         }
573         return true;
574 }
575
576
577 /*---------------------------------------------------------------------------
578
579   Function:   ft1000_hbchk
580   Description: This function will perform the heart beat check of the DSP as
581   well as the ASIC.
582   Input:
583   dev    - device structure
584   Output:
585   none
586
587   -------------------------------------------------------------------------*/
588 static void ft1000_hbchk(u_long data)
589 {
590         struct net_device *dev = (struct net_device *)data;
591
592         struct ft1000_info *info;
593         u16 tempword;
594
595         info = netdev_priv(dev);
596
597         if (info->CardReady == 1) {
598                 /* Perform dsp heartbeat check */
599                 if (info->AsicID == ELECTRABUZZ_ID) {
600                         tempword = ft1000_read_dpram(dev, FT1000_HI_HO);
601                 } else {
602                         tempword =
603                                 ntohs(ft1000_read_dpram_mag_16
604                                       (dev, FT1000_MAG_HI_HO,
605                                        FT1000_MAG_HI_HO_INDX));
606                 }
607                 pr_debug("hi_ho value = 0x%x\n", tempword);
608                 /* Let's perform another check if ho is not detected */
609                 if (tempword != ho) {
610                         if (info->AsicID == ELECTRABUZZ_ID)
611                                 tempword = ft1000_read_dpram(dev, FT1000_HI_HO);
612                         else
613                                 tempword = ntohs(ft1000_read_dpram_mag_16(dev,
614                                                         FT1000_MAG_HI_HO,
615                                                         FT1000_MAG_HI_HO_INDX));
616                 }
617                 if (tempword != ho) {
618                         pr_info("heartbeat failed - no ho detected\n");
619                         ft1000_read_dsp_timer(dev, info);
620                         info->DrvErrNum = DSP_HB_INFO;
621                         if (ft1000_reset_card(dev) == 0) {
622                                 pr_info("Hardware Failure Detected - PC Card disabled\n");
623                                 info->ProgConStat = 0xff;
624                                 return;
625                         }
626                         /* Schedule this module to run every 2 seconds */
627                         poll_timer.expires = jiffies + (2*HZ);
628                         poll_timer.data = (u_long)dev;
629                         add_timer(&poll_timer);
630                         return;
631                 }
632
633                 tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL);
634                 /* Let's check doorbell again if fail */
635                 if (tempword & FT1000_DB_HB)
636                         tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL);
637
638                 if (tempword & FT1000_DB_HB) {
639                         pr_info("heartbeat doorbell not clear by firmware\n");
640                         ft1000_read_dsp_timer(dev, info);
641                         info->DrvErrNum = DSP_HB_INFO;
642                         if (ft1000_reset_card(dev) == 0) {
643                                 pr_info("Hardware Failure Detected - PC Card disabled\n");
644                                 info->ProgConStat = 0xff;
645                                 return;
646                         }
647                         /* Schedule this module to run every 2 seconds */
648                         poll_timer.expires = jiffies + (2*HZ);
649                         poll_timer.data = (u_long)dev;
650                         add_timer(&poll_timer);
651                         return;
652                 }
653                 /*
654                  * Set dedicated area to hi and ring appropriate doorbell
655                  * according to hi/ho heartbeat protocol
656                  */
657                 if (info->AsicID == ELECTRABUZZ_ID) {
658                         ft1000_write_dpram(dev, FT1000_HI_HO, hi);
659                 } else {
660                         ft1000_write_dpram_mag_16(dev, FT1000_MAG_HI_HO, hi_mag,
661                                                   FT1000_MAG_HI_HO_INDX);
662                 }
663
664                 if (info->AsicID == ELECTRABUZZ_ID) {
665                         tempword = ft1000_read_dpram(dev, FT1000_HI_HO);
666                 } else {
667                         tempword =
668                                 ntohs(ft1000_read_dpram_mag_16
669                                       (dev, FT1000_MAG_HI_HO,
670                                        FT1000_MAG_HI_HO_INDX));
671                 }
672                 /* Let's write hi again if fail */
673                 if (tempword != hi) {
674                         if (info->AsicID == ELECTRABUZZ_ID)
675                                 ft1000_write_dpram(dev, FT1000_HI_HO, hi);
676                         else
677                                 ft1000_write_dpram_mag_16(dev, FT1000_MAG_HI_HO,
678                                                 hi_mag, FT1000_MAG_HI_HO_INDX);
679
680                         if (info->AsicID == ELECTRABUZZ_ID)
681                                 tempword = ft1000_read_dpram(dev, FT1000_HI_HO);
682                         else
683                                 tempword = ntohs(ft1000_read_dpram_mag_16(dev,
684                                                         FT1000_MAG_HI_HO,
685                                                         FT1000_MAG_HI_HO_INDX));
686                 }
687
688                 if (tempword != hi) {
689                         pr_info("heartbeat failed - cannot write hi into DPRAM\n");
690                         ft1000_read_dsp_timer(dev, info);
691                         info->DrvErrNum = DSP_HB_INFO;
692                         if (ft1000_reset_card(dev) == 0) {
693                                 pr_info("Hardware Failure Detected - PC Card disabled\n");
694                                 info->ProgConStat = 0xff;
695                                 return;
696                         }
697                         /* Schedule this module to run every 2 seconds */
698                         poll_timer.expires = jiffies + (2*HZ);
699                         poll_timer.data = (u_long)dev;
700                         add_timer(&poll_timer);
701                         return;
702                 }
703                 ft1000_write_reg(dev, FT1000_REG_DOORBELL, FT1000_DB_HB);
704
705         }
706
707         /* Schedule this module to run every 2 seconds */
708         poll_timer.expires = jiffies + (2 * HZ);
709         poll_timer.data = (u_long)dev;
710         add_timer(&poll_timer);
711 }
712
713 /*---------------------------------------------------------------------------
714
715   Function:   ft1000_send_cmd
716   Description:
717   Input:
718   Output:
719
720   -------------------------------------------------------------------------*/
721 static void ft1000_send_cmd(struct net_device *dev, u16 *ptempbuffer, int size,
722                             u16 qtype)
723 {
724         struct ft1000_info *info = netdev_priv(dev);
725         int i;
726         u16 tempword;
727         unsigned long flags;
728
729         size += sizeof(struct pseudo_hdr);
730         /* check for odd byte and increment to 16-bit word align value */
731         if ((size & 0x0001))
732                 size++;
733         pr_debug("total length = %d\n", size);
734         pr_debug("length = %d\n", ntohs(*ptempbuffer));
735         /*
736          * put message into slow queue area
737          * All messages are in the form total_len + pseudo header + message body
738          */
739         spin_lock_irqsave(&info->dpram_lock, flags);
740
741         /* Make sure SLOWQ doorbell is clear */
742         tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL);
743         i = 0;
744         while (tempword & FT1000_DB_DPRAM_TX) {
745                 mdelay(10);
746                 i++;
747                 if (i == 10) {
748                         spin_unlock_irqrestore(&info->dpram_lock, flags);
749                         return;
750                 }
751                 tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL);
752         }
753
754         if (info->AsicID == ELECTRABUZZ_ID) {
755                 ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
756                                  FT1000_DPRAM_TX_BASE);
757                 /* Write total length to dpram */
758                 ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, size);
759                 /* Write pseudo header and messgae body */
760                 for (i = 0; i < (size >> 1); i++) {
761                         pr_debug("data %d = 0x%x\n", i, *ptempbuffer);
762                         tempword = htons(*ptempbuffer++);
763                         ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, tempword);
764                 }
765         } else {
766                 ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
767                                  FT1000_DPRAM_MAG_TX_BASE);
768                 /* Write total length to dpram */
769                 ft1000_write_reg(dev, FT1000_REG_MAG_DPDATAH, htons(size));
770                 /* Write pseudo header and messgae body */
771                 ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
772                                  FT1000_DPRAM_MAG_TX_BASE + 1);
773                 for (i = 0; i < (size >> 2); i++) {
774                         pr_debug("data = 0x%x\n", *ptempbuffer);
775                         outw(*ptempbuffer++,
776                              dev->base_addr + FT1000_REG_MAG_DPDATAL);
777                         pr_debug("data = 0x%x\n", *ptempbuffer);
778                         outw(*ptempbuffer++,
779                              dev->base_addr + FT1000_REG_MAG_DPDATAH);
780                 }
781                 pr_debug("data = 0x%x\n", *ptempbuffer);
782                 outw(*ptempbuffer++, dev->base_addr + FT1000_REG_MAG_DPDATAL);
783                 pr_debug("data = 0x%x\n", *ptempbuffer);
784                 outw(*ptempbuffer++, dev->base_addr + FT1000_REG_MAG_DPDATAH);
785         }
786         spin_unlock_irqrestore(&info->dpram_lock, flags);
787
788         /* ring doorbell to notify DSP that we have a message ready */
789         ft1000_write_reg(dev, FT1000_REG_DOORBELL, FT1000_DB_DPRAM_TX);
790 }
791
792 /*---------------------------------------------------------------------------
793
794   Function:   ft1000_receive_cmd
795   Description: This function will read a message from the dpram area.
796   Input:
797   dev - network device structure
798   pbuffer - caller supply address to buffer
799   pnxtph - pointer to next pseudo header
800   Output:
801   Status = 0 (unsuccessful)
802   = 1 (successful)
803
804   -------------------------------------------------------------------------*/
805 static bool ft1000_receive_cmd(struct net_device *dev, u16 *pbuffer,
806                                int maxsz, u16 *pnxtph)
807 {
808         struct ft1000_info *info = netdev_priv(dev);
809         u16 size;
810         u16 *ppseudohdr;
811         int i;
812         u16 tempword;
813         unsigned long flags;
814
815         if (info->AsicID == ELECTRABUZZ_ID) {
816                 size = ft1000_read_dpram(dev, *pnxtph)
817                         + sizeof(struct pseudo_hdr);
818         } else {
819                 size = ntohs(ft1000_read_dpram_mag_16(dev, FT1000_MAG_PH_LEN,
820                                                       FT1000_MAG_PH_LEN_INDX))
821                                 + sizeof(struct pseudo_hdr);
822         }
823         if (size > maxsz) {
824                 pr_debug("Invalid command length = %d\n", size);
825                 return false;
826         }
827         ppseudohdr = (u16 *)pbuffer;
828         spin_lock_irqsave(&info->dpram_lock, flags);
829         if (info->AsicID == ELECTRABUZZ_ID) {
830                 ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
831                                  FT1000_DPRAM_RX_BASE + 2);
832                 for (i = 0; i <= (size >> 1); i++) {
833                         tempword =
834                                 ft1000_read_reg(dev, FT1000_REG_DPRAM_DATA);
835                         *pbuffer++ = ntohs(tempword);
836                 }
837         } else {
838                 ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
839                                  FT1000_DPRAM_MAG_RX_BASE);
840                 *pbuffer = inw(dev->base_addr + FT1000_REG_MAG_DPDATAH);
841                 pr_debug("received data = 0x%x\n", *pbuffer);
842                 pbuffer++;
843                 ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
844                                  FT1000_DPRAM_MAG_RX_BASE + 1);
845                 for (i = 0; i <= (size >> 2); i++) {
846                         *pbuffer =
847                                 inw(dev->base_addr +
848                                     FT1000_REG_MAG_DPDATAL);
849                         pbuffer++;
850                         *pbuffer =
851                                 inw(dev->base_addr +
852                                     FT1000_REG_MAG_DPDATAH);
853                         pbuffer++;
854                 }
855                 /* copy odd aligned word */
856                 *pbuffer = inw(dev->base_addr + FT1000_REG_MAG_DPDATAL);
857                 pr_debug("received data = 0x%x\n", *pbuffer);
858                 pbuffer++;
859                 *pbuffer = inw(dev->base_addr + FT1000_REG_MAG_DPDATAH);
860                 pr_debug("received data = 0x%x\n", *pbuffer);
861                 pbuffer++;
862         }
863         if (size & 0x0001) {
864                 /* copy odd byte from fifo */
865                 tempword = ft1000_read_reg(dev, FT1000_REG_DPRAM_DATA);
866                 *pbuffer = ntohs(tempword);
867         }
868         spin_unlock_irqrestore(&info->dpram_lock, flags);
869
870         /*
871          * Check if pseudo header checksum is good
872          * Calculate pseudo header checksum
873          */
874         tempword = *ppseudohdr++;
875         for (i = 1; i < 7; i++)
876                 tempword ^= *ppseudohdr++;
877         if (tempword != *ppseudohdr) {
878                 pr_debug("Pseudo header checksum mismatch\n");
879                 /* Drop this message */
880                 return false;
881         }
882         return true;
883 }
884
885 /*---------------------------------------------------------------------------
886
887   Function:   ft1000_proc_drvmsg
888   Description: This function will process the various driver messages.
889   Input:
890   dev    - device structure
891   pnxtph - pointer to next pseudo header
892   Output:
893   none
894
895   -------------------------------------------------------------------------*/
896 static void ft1000_proc_drvmsg(struct net_device *dev)
897 {
898         struct ft1000_info *info = netdev_priv(dev);
899         u16 msgtype;
900         u16 tempword;
901         struct media_msg *pmediamsg;
902         struct dsp_init_msg *pdspinitmsg;
903         struct drv_msg *pdrvmsg;
904         u16 len;
905         u16 i;
906         struct prov_record *ptr;
907         struct pseudo_hdr *ppseudo_hdr;
908         u16 *pmsg;
909         struct timeval tv;
910         union {
911                 u8 byte[2];
912                 u16 wrd;
913         } convert;
914
915         if (info->AsicID == ELECTRABUZZ_ID)
916                 tempword = FT1000_DPRAM_RX_BASE+2;
917         else
918                 tempword = FT1000_DPRAM_MAG_RX_BASE;
919
920         if (ft1000_receive_cmd(dev, &cmdbuffer[0], MAX_CMD_SQSIZE, &tempword)) {
921
922                 /*
923                  * Get the message type which is total_len + PSEUDO header
924                  * + msgtype + message body
925                  */
926                 pdrvmsg = (struct drv_msg *)&cmdbuffer[0];
927                 msgtype = ntohs(pdrvmsg->type);
928                 pr_debug("Command message type = 0x%x\n", msgtype);
929                 switch (msgtype) {
930                 case DSP_PROVISION:
931                         pr_debug("Got a provisioning request message from DSP\n");
932                         mdelay(25);
933                         while (list_empty(&info->prov_list) == 0) {
934                                 pr_debug("Sending a provisioning message\n");
935                                 /* Make sure SLOWQ doorbell is clear */
936                                 tempword = ft1000_read_reg(dev,
937                                                            FT1000_REG_DOORBELL);
938                                 i = 0;
939                                 while (tempword & FT1000_DB_DPRAM_TX) {
940                                         mdelay(5);
941                                         i++;
942                                         if (i == 10)
943                                                 break;
944                                 }
945                                 ptr = list_entry(info->prov_list.next,
946                                                  struct prov_record, list);
947                                 len = *(u16 *)ptr->pprov_data;
948                                 len = htons(len);
949
950                                 pmsg = (u16 *)ptr->pprov_data;
951                                 ppseudo_hdr = (struct pseudo_hdr *)pmsg;
952                                 /* Insert slow queue sequence number */
953                                 ppseudo_hdr->seq_num = info->squeseqnum++;
954                                 ppseudo_hdr->portsrc = 0;
955                                 /* Calculate new checksum */
956                                 ppseudo_hdr->checksum = *pmsg++;
957                                 pr_debug("checksum = 0x%x\n",
958                                          ppseudo_hdr->checksum);
959                                 for (i = 1; i < 7; i++) {
960                                         ppseudo_hdr->checksum ^= *pmsg++;
961                                         pr_debug("checksum = 0x%x\n",
962                                                  ppseudo_hdr->checksum);
963                                 }
964
965                                 ft1000_send_cmd(dev, (u16 *)ptr->pprov_data,
966                                                 len, SLOWQ_TYPE);
967                                 list_del(&ptr->list);
968                                 kfree(ptr->pprov_data);
969                                 kfree(ptr);
970                         }
971                         /*
972                          * Indicate adapter is ready to take application
973                          * messages after all provisioning messages are sent
974                          */
975                         info->CardReady = 1;
976                         break;
977                 case MEDIA_STATE:
978                         pmediamsg = (struct media_msg *)&cmdbuffer[0];
979                         if (info->ProgConStat != 0xFF) {
980                                 if (pmediamsg->state) {
981                                         pr_debug("Media is up\n");
982                                         if (info->mediastate == 0) {
983                                                 netif_carrier_on(dev);
984                                                 netif_wake_queue(dev);
985                                                 info->mediastate = 1;
986                                                 do_gettimeofday(&tv);
987                                                 info->ConTm = tv.tv_sec;
988                                         }
989                                 } else {
990                                         pr_debug("Media is down\n");
991                                         if (info->mediastate == 1) {
992                                                 info->mediastate = 0;
993                                                 netif_carrier_off(dev);
994                                                 netif_stop_queue(dev);
995                                                 info->ConTm = 0;
996                                         }
997                                 }
998                         } else {
999                                 pr_debug("Media is down\n");
1000                                 if (info->mediastate == 1) {
1001                                         info->mediastate = 0;
1002                                         netif_carrier_off(dev);
1003                                         netif_stop_queue(dev);
1004                                         info->ConTm = 0;
1005                                 }
1006                         }
1007                         break;
1008                 case DSP_INIT_MSG:
1009                         pdspinitmsg = (struct dsp_init_msg *)&cmdbuffer[0];
1010                         memcpy(info->DspVer, pdspinitmsg->DspVer, DSPVERSZ);
1011                         pr_debug("DSPVER = 0x%2x 0x%2x 0x%2x 0x%2x\n",
1012                                  info->DspVer[0], info->DspVer[1],
1013                                  info->DspVer[2], info->DspVer[3]);
1014                         memcpy(info->HwSerNum, pdspinitmsg->HwSerNum,
1015                                HWSERNUMSZ);
1016                         memcpy(info->Sku, pdspinitmsg->Sku, SKUSZ);
1017                         memcpy(info->eui64, pdspinitmsg->eui64, EUISZ);
1018                         dev->dev_addr[0] = info->eui64[0];
1019                         dev->dev_addr[1] = info->eui64[1];
1020                         dev->dev_addr[2] = info->eui64[2];
1021                         dev->dev_addr[3] = info->eui64[5];
1022                         dev->dev_addr[4] = info->eui64[6];
1023                         dev->dev_addr[5] = info->eui64[7];
1024
1025                         if (ntohs(pdspinitmsg->length) ==
1026                             (sizeof(struct dsp_init_msg) - 20)) {
1027                                 memcpy(info->ProductMode,
1028                                        pdspinitmsg->ProductMode, MODESZ);
1029                                 memcpy(info->RfCalVer, pdspinitmsg->RfCalVer,
1030                                        CALVERSZ);
1031                                 memcpy(info->RfCalDate, pdspinitmsg->RfCalDate,
1032                                        CALDATESZ);
1033                                 pr_debug("RFCalVer = 0x%2x 0x%2x\n",
1034                                          info->RfCalVer[0], info->RfCalVer[1]);
1035                         }
1036
1037                         break;
1038                 case DSP_STORE_INFO:
1039                         pr_debug("Got DSP_STORE_INFO\n");
1040                         tempword = ntohs(pdrvmsg->length);
1041                         info->DSPInfoBlklen = tempword;
1042                         if (tempword < (MAX_DSP_SESS_REC - 4)) {
1043                                 pmsg = (u16 *)&pdrvmsg->data[0];
1044                                 for (i = 0; i < ((tempword + 1) / 2); i++) {
1045                                         pr_debug("dsp info data = 0x%x\n",
1046                                                  *pmsg);
1047                                         info->DSPInfoBlk[i + 10] = *pmsg++;
1048                                 }
1049                         }
1050                         break;
1051                 case DSP_GET_INFO:
1052                         pr_debug("Got DSP_GET_INFO\n");
1053                         /*
1054                          * copy dsp info block to dsp
1055                          * allow any outstanding ioctl to finish
1056                          */
1057                         mdelay(10);
1058                         tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL);
1059                         if (tempword & FT1000_DB_DPRAM_TX) {
1060                                 mdelay(10);
1061                                 tempword = ft1000_read_reg(dev,
1062                                                            FT1000_REG_DOORBELL);
1063                                 if (tempword & FT1000_DB_DPRAM_TX)
1064                                         mdelay(10);
1065                         }
1066
1067                         if ((tempword & FT1000_DB_DPRAM_TX) == 0) {
1068                                 /*
1069                                  * Put message into Slow Queue
1070                                  * Form Pseudo header
1071                                  */
1072                                 pmsg = (u16 *)info->DSPInfoBlk;
1073                                 ppseudo_hdr = (struct pseudo_hdr *)pmsg;
1074                                 ppseudo_hdr->length =
1075                                         htons(info->DSPInfoBlklen + 4);
1076                                 ppseudo_hdr->source = 0x10;
1077                                 ppseudo_hdr->destination = 0x20;
1078                                 ppseudo_hdr->portdest = 0;
1079                                 ppseudo_hdr->portsrc = 0;
1080                                 ppseudo_hdr->sh_str_id = 0;
1081                                 ppseudo_hdr->control = 0;
1082                                 ppseudo_hdr->rsvd1 = 0;
1083                                 ppseudo_hdr->rsvd2 = 0;
1084                                 ppseudo_hdr->qos_class = 0;
1085                                 /* Insert slow queue sequence number */
1086                                 ppseudo_hdr->seq_num = info->squeseqnum++;
1087                                 /* Insert application id */
1088                                 ppseudo_hdr->portsrc = 0;
1089                                 /* Calculate new checksum */
1090                                 ppseudo_hdr->checksum = *pmsg++;
1091                                 for (i = 1; i < 7; i++)
1092                                         ppseudo_hdr->checksum ^= *pmsg++;
1093
1094                                 info->DSPInfoBlk[8] = 0x7200;
1095                                 info->DSPInfoBlk[9] =
1096                                         htons(info->DSPInfoBlklen);
1097                                 ft1000_send_cmd(dev, info->DSPInfoBlk,
1098                                                 (u16)(info->DSPInfoBlklen+4),
1099                                                 0);
1100                         }
1101
1102                         break;
1103                 case GET_DRV_ERR_RPT_MSG:
1104                         pr_debug("Got GET_DRV_ERR_RPT_MSG\n");
1105                         /*
1106                          * copy driver error message to dsp
1107                          * allow any outstanding ioctl to finish
1108                          */
1109                         mdelay(10);
1110                         tempword = ft1000_read_reg(dev, FT1000_REG_DOORBELL);
1111                         if (tempword & FT1000_DB_DPRAM_TX) {
1112                                 mdelay(10);
1113                                 tempword = ft1000_read_reg(dev,
1114                                                            FT1000_REG_DOORBELL);
1115                                 if (tempword & FT1000_DB_DPRAM_TX)
1116                                         mdelay(10);
1117                         }
1118
1119                         if ((tempword & FT1000_DB_DPRAM_TX) == 0) {
1120                                 /*
1121                                  * Put message into Slow Queue
1122                                  * Form Pseudo header
1123                                  */
1124                                 pmsg = (u16 *)&tempbuffer[0];
1125                                 ppseudo_hdr = (struct pseudo_hdr *)pmsg;
1126                                 ppseudo_hdr->length = htons(0x0012);
1127                                 ppseudo_hdr->source = 0x10;
1128                                 ppseudo_hdr->destination = 0x20;
1129                                 ppseudo_hdr->portdest = 0;
1130                                 ppseudo_hdr->portsrc = 0;
1131                                 ppseudo_hdr->sh_str_id = 0;
1132                                 ppseudo_hdr->control = 0;
1133                                 ppseudo_hdr->rsvd1 = 0;
1134                                 ppseudo_hdr->rsvd2 = 0;
1135                                 ppseudo_hdr->qos_class = 0;
1136                                 /* Insert slow queue sequence number */
1137                                 ppseudo_hdr->seq_num = info->squeseqnum++;
1138                                 /* Insert application id */
1139                                 ppseudo_hdr->portsrc = 0;
1140                                 /* Calculate new checksum */
1141                                 ppseudo_hdr->checksum = *pmsg++;
1142                                 for (i = 1; i < 7; i++)
1143                                         ppseudo_hdr->checksum ^= *pmsg++;
1144
1145                                 pmsg = (u16 *)&tempbuffer[16];
1146                                 *pmsg++ = htons(RSP_DRV_ERR_RPT_MSG);
1147                                 *pmsg++ = htons(0x000e);
1148                                 *pmsg++ = htons(info->DSP_TIME[0]);
1149                                 *pmsg++ = htons(info->DSP_TIME[1]);
1150                                 *pmsg++ = htons(info->DSP_TIME[2]);
1151                                 *pmsg++ = htons(info->DSP_TIME[3]);
1152                                 convert.byte[0] = info->DspVer[0];
1153                                 convert.byte[1] = info->DspVer[1];
1154                                 *pmsg++ = convert.wrd;
1155                                 convert.byte[0] = info->DspVer[2];
1156                                 convert.byte[1] = info->DspVer[3];
1157                                 *pmsg++ = convert.wrd;
1158                                 *pmsg++ = htons(info->DrvErrNum);
1159
1160                                 ft1000_send_cmd(dev, (u16 *)&tempbuffer[0],
1161                                                 (u16)(0x0012), 0);
1162                                 info->DrvErrNum = 0;
1163                         }
1164
1165                         break;
1166                 default:
1167                         break;
1168                 }
1169         }
1170 }
1171
1172 /*---------------------------------------------------------------------------
1173
1174   Function:   ft1000_parse_dpram_msg
1175   Description: This function will parse the message received from the DSP
1176   via the DPRAM interface.
1177   Input:
1178   dev    - device structure
1179   Output:
1180   status - FAILURE
1181   SUCCESS
1182
1183   -------------------------------------------------------------------------*/
1184 static int ft1000_parse_dpram_msg(struct net_device *dev)
1185 {
1186         struct ft1000_info *info = netdev_priv(dev);
1187         u16 doorbell;
1188         u16 portid;
1189         u16 nxtph;
1190         u16 total_len;
1191         int i = 0;
1192         unsigned long flags;
1193
1194         doorbell = ft1000_read_reg(dev, FT1000_REG_DOORBELL);
1195         pr_debug("Doorbell = 0x%x\n", doorbell);
1196
1197         if (doorbell & FT1000_ASIC_RESET_REQ) {
1198                 /* Copy DSP session record from info block */
1199                 spin_lock_irqsave(&info->dpram_lock, flags);
1200                 if (info->AsicID == ELECTRABUZZ_ID) {
1201                         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
1202                                          FT1000_DPRAM_RX_BASE);
1203                         for (i = 0; i < MAX_DSP_SESS_REC; i++) {
1204                                 ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA,
1205                                                  info->DSPSess.Rec[i]);
1206                         }
1207                 } else {
1208                         ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR,
1209                                          FT1000_DPRAM_MAG_RX_BASE);
1210                         for (i = 0; i < MAX_DSP_SESS_REC / 2; i++) {
1211                                 outl(info->DSPSess.MagRec[i],
1212                                      dev->base_addr + FT1000_REG_MAG_DPDATA);
1213                         }
1214                 }
1215                 spin_unlock_irqrestore(&info->dpram_lock, flags);
1216
1217                 /* clear ASIC RESET request */
1218                 ft1000_write_reg(dev, FT1000_REG_DOORBELL,
1219                                  FT1000_ASIC_RESET_REQ);
1220                 pr_debug("Got an ASIC RESET Request\n");
1221                 ft1000_write_reg(dev, FT1000_REG_DOORBELL,
1222                                  FT1000_ASIC_RESET_DSP);
1223
1224                 if (info->AsicID == MAGNEMITE_ID) {
1225                         /* Setting MAGNEMITE ASIC to big endian mode */
1226                         ft1000_write_reg(dev, FT1000_REG_SUP_CTRL,
1227                                          HOST_INTF_BE);
1228                 }
1229         }
1230
1231         if (doorbell & FT1000_DSP_ASIC_RESET) {
1232                 pr_debug("Got a dsp ASIC reset message\n");
1233                 ft1000_write_reg(dev, FT1000_REG_DOORBELL,
1234                                  FT1000_DSP_ASIC_RESET);
1235                 udelay(200);
1236                 return SUCCESS;
1237         }
1238
1239         if (doorbell & FT1000_DB_DPRAM_RX) {
1240                 pr_debug("Got a slow queue message\n");
1241                 nxtph = FT1000_DPRAM_RX_BASE + 2;
1242                 if (info->AsicID == ELECTRABUZZ_ID) {
1243                         total_len =
1244                                 ft1000_read_dpram(dev, FT1000_DPRAM_RX_BASE);
1245                 } else {
1246                         total_len =
1247                                 ntohs(ft1000_read_dpram_mag_16
1248                                       (dev, FT1000_MAG_TOTAL_LEN,
1249                                        FT1000_MAG_TOTAL_LEN_INDX));
1250                 }
1251                 pr_debug("total length = %d\n", total_len);
1252                 if ((total_len < MAX_CMD_SQSIZE)
1253                                 && (total_len > sizeof(struct pseudo_hdr))) {
1254                         total_len += nxtph;
1255                         /*
1256                          * ft1000_read_reg will return a value that needs to be
1257                          * byteswap in order to get DSP_QID_OFFSET.
1258                          */
1259                         if (info->AsicID == ELECTRABUZZ_ID) {
1260                                 portid = (ft1000_read_dpram(dev, DSP_QID_OFFSET
1261                                                 + FT1000_DPRAM_RX_BASE + 2)
1262                                                 >> 8) & 0xff;
1263                         } else {
1264                                 portid =
1265                                         ft1000_read_dpram_mag_16
1266                                          (dev, FT1000_MAG_PORT_ID,
1267                                           FT1000_MAG_PORT_ID_INDX) & 0xff;
1268                         }
1269                         pr_debug("DSP_QID = 0x%x\n", portid);
1270
1271                         if (portid == DRIVERID) {
1272                                 /*
1273                                  * We are assumming one driver message from the
1274                                  * DSP at a time.
1275                                  */
1276                                 ft1000_proc_drvmsg(dev);
1277                         }
1278                 }
1279                 ft1000_write_reg(dev, FT1000_REG_DOORBELL, FT1000_DB_DPRAM_RX);
1280         }
1281
1282         if (doorbell & FT1000_DB_COND_RESET) {
1283                 /* Reset ASIC and DSP */
1284                 ft1000_read_dsp_timer(dev, info);
1285                 info->DrvErrNum = DSP_CONDRESET_INFO;
1286                 pr_debug("DSP conditional reset requested\n");
1287                 ft1000_reset_card(dev);
1288                 ft1000_write_reg(dev, FT1000_REG_DOORBELL,
1289                                  FT1000_DB_COND_RESET);
1290         }
1291         /* let's clear any unexpected doorbells from DSP */
1292         doorbell =
1293                 doorbell & ~(FT1000_DB_DPRAM_RX | FT1000_ASIC_RESET_REQ |
1294                              FT1000_DB_COND_RESET | 0xff00);
1295         if (doorbell) {
1296                 pr_debug("Clearing unexpected doorbell = 0x%x\n", doorbell);
1297                 ft1000_write_reg(dev, FT1000_REG_DOORBELL, doorbell);
1298         }
1299
1300         return SUCCESS;
1301
1302 }
1303
1304 /*---------------------------------------------------------------------------
1305
1306   Function:   ft1000_flush_fifo
1307   Description: This function will flush one packet from the downlink
1308   FIFO.
1309   Input:
1310   dev      - device structure
1311   drv_err  - driver error causing the flush fifo
1312   Output:
1313   None.
1314
1315   -------------------------------------------------------------------------*/
1316 static void ft1000_flush_fifo(struct net_device *dev, u16 DrvErrNum)
1317 {
1318         struct ft1000_info *info = netdev_priv(dev);
1319         struct ft1000_pcmcia *pcmcia = info->priv;
1320         u16 i;
1321         u32 templong;
1322         u16 tempword;
1323
1324         if (pcmcia->PktIntfErr > MAX_PH_ERR) {
1325                 ft1000_read_dsp_timer(dev, info);
1326                 info->DrvErrNum = DrvErrNum;
1327                 ft1000_reset_card(dev);
1328                 return;
1329         }
1330         /* Flush corrupted pkt from FIFO */
1331         i = 0;
1332         do {
1333                 if (info->AsicID == ELECTRABUZZ_ID) {
1334                         tempword =
1335                                 ft1000_read_reg(dev, FT1000_REG_DFIFO);
1336                         tempword =
1337                                 ft1000_read_reg(dev, FT1000_REG_DFIFO_STAT);
1338                 } else {
1339                         templong =
1340                                 inl(dev->base_addr + FT1000_REG_MAG_DFR);
1341                         tempword =
1342                                 inw(dev->base_addr + FT1000_REG_MAG_DFSR);
1343                 }
1344                 i++;
1345                 /*
1346                  * This should never happen unless the ASIC is broken.
1347                  * We must reset to recover.
1348                  */
1349                 if ((i > 2048) || (tempword == 0)) {
1350                         ft1000_read_dsp_timer(dev, info);
1351                         if (tempword == 0) {
1352                                 /*
1353                                  * Let's check if ASIC reads are still ok by
1354                                  * reading the Mask register which is never zero
1355                                  * at this point of the code.
1356                                  */
1357                                 tempword =
1358                                         inw(dev->base_addr +
1359                                             FT1000_REG_SUP_IMASK);
1360                                 if (tempword == 0) {
1361                                         /*
1362                                          * This indicates that we can not
1363                                          * communicate with the ASIC
1364                                          */
1365                                         info->DrvErrNum = FIFO_FLUSH_BADCNT;
1366                                 } else {
1367                                         /*
1368                                          * Let's assume that we really flush
1369                                          * the FIFO
1370                                          */
1371                                         pcmcia->PktIntfErr++;
1372                                         return;
1373                                 }
1374                         } else {
1375                                 info->DrvErrNum = FIFO_FLUSH_MAXLIMIT;
1376                         }
1377                         return;
1378                 }
1379                 tempword = inw(dev->base_addr + FT1000_REG_SUP_STAT);
1380         } while ((tempword & 0x03) != 0x03);
1381         if (info->AsicID == ELECTRABUZZ_ID) {
1382                 i++;
1383                 pr_debug("Flushing FIFO complete = %x\n", tempword);
1384                 /* Flush last word in FIFO. */
1385                 tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO);
1386                 /* Update FIFO counter for DSP */
1387                 i = i * 2;
1388                 pr_debug("Flush Data byte count to dsp = %d\n", i);
1389                 info->fifo_cnt += i;
1390                 ft1000_write_dpram(dev, FT1000_FIFO_LEN,
1391                                    info->fifo_cnt);
1392         } else {
1393                 pr_debug("Flushing FIFO complete = %x\n", tempword);
1394                 /* Flush last word in FIFO */
1395                 templong = inl(dev->base_addr + FT1000_REG_MAG_DFR);
1396                 tempword = inw(dev->base_addr + FT1000_REG_SUP_STAT);
1397                 pr_debug("FT1000_REG_SUP_STAT = 0x%x\n", tempword);
1398                 tempword = inw(dev->base_addr + FT1000_REG_MAG_DFSR);
1399                 pr_debug("FT1000_REG_MAG_DFSR = 0x%x\n", tempword);
1400         }
1401         if (DrvErrNum)
1402                 pcmcia->PktIntfErr++;
1403 }
1404
1405 /*---------------------------------------------------------------------------
1406
1407   Function:   ft1000_copy_up_pkt
1408   Description: This function will pull Flarion packets out of the Downlink
1409   FIFO and convert it to an ethernet packet.  The ethernet packet will
1410   then be deliver to the TCP/IP stack.
1411   Input:
1412   dev    - device structure
1413   Output:
1414   status - FAILURE
1415   SUCCESS
1416
1417   -------------------------------------------------------------------------*/
1418 static int ft1000_copy_up_pkt(struct net_device *dev)
1419 {
1420         u16 tempword;
1421         struct ft1000_info *info = netdev_priv(dev);
1422         u16 len;
1423         struct sk_buff *skb;
1424         u16 i;
1425         u8 *pbuffer = NULL;
1426         u8 *ptemp = NULL;
1427         u16 chksum;
1428         u32 *ptemplong;
1429         u32 templong;
1430
1431         /* Read length */
1432         if (info->AsicID == ELECTRABUZZ_ID) {
1433                 tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO);
1434                 len = tempword;
1435         } else {
1436                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRL);
1437                 len = ntohs(tempword);
1438         }
1439         chksum = tempword;
1440         pr_debug("Number of Bytes in FIFO = %d\n", len);
1441
1442         if (len > ENET_MAX_SIZE) {
1443                 pr_debug("size of ethernet packet invalid\n");
1444                 if (info->AsicID == MAGNEMITE_ID) {
1445                         /* Read High word to complete 32 bit access */
1446                         tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH);
1447                 }
1448                 ft1000_flush_fifo(dev, DSP_PKTLEN_INFO);
1449                 info->stats.rx_errors++;
1450                 return FAILURE;
1451         }
1452
1453         skb = dev_alloc_skb(len + 12 + 2);
1454
1455         if (skb == NULL) {
1456                 /* Read High word to complete 32 bit access */
1457                 if (info->AsicID == MAGNEMITE_ID)
1458                         tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH);
1459
1460                 ft1000_flush_fifo(dev, 0);
1461                 info->stats.rx_errors++;
1462                 return FAILURE;
1463         }
1464         pbuffer = (u8 *)skb_put(skb, len + 12);
1465
1466         /* Pseudo header */
1467         if (info->AsicID == ELECTRABUZZ_ID) {
1468                 for (i = 1; i < 7; i++) {
1469                         tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO);
1470                         chksum ^= tempword;
1471                 }
1472                 /* read checksum value */
1473                 tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO);
1474         } else {
1475                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH);
1476                 pr_debug("Pseudo = 0x%x\n", tempword);
1477                 chksum ^= tempword;
1478
1479                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRL);
1480                 pr_debug("Pseudo = 0x%x\n", tempword);
1481                 chksum ^= tempword;
1482
1483                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH);
1484                 pr_debug("Pseudo = 0x%x\n", tempword);
1485                 chksum ^= tempword;
1486
1487                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRL);
1488                 pr_debug("Pseudo = 0x%x\n", tempword);
1489                 chksum ^= tempword;
1490
1491                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH);
1492                 pr_debug("Pseudo = 0x%x\n", tempword);
1493                 chksum ^= tempword;
1494
1495                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRL);
1496                 pr_debug("Pseudo = 0x%x\n", tempword);
1497                 chksum ^= tempword;
1498
1499                 /* read checksum value */
1500                 tempword = ft1000_read_reg(dev, FT1000_REG_MAG_DFRH);
1501                 pr_debug("Pseudo = 0x%x\n", tempword);
1502         }
1503
1504         if (chksum != tempword) {
1505                 pr_debug("Packet checksum mismatch 0x%x 0x%x\n",
1506                          chksum, tempword);
1507                 ft1000_flush_fifo(dev, DSP_PKTPHCKSUM_INFO);
1508                 info->stats.rx_errors++;
1509                 kfree_skb(skb);
1510                 return FAILURE;
1511         }
1512         /* subtract the number of bytes read already */
1513         ptemp = pbuffer;
1514
1515         /* fake MAC address */
1516         *pbuffer++ = dev->dev_addr[0];
1517         *pbuffer++ = dev->dev_addr[1];
1518         *pbuffer++ = dev->dev_addr[2];
1519         *pbuffer++ = dev->dev_addr[3];
1520         *pbuffer++ = dev->dev_addr[4];
1521         *pbuffer++ = dev->dev_addr[5];
1522         *pbuffer++ = 0x00;
1523         *pbuffer++ = 0x07;
1524         *pbuffer++ = 0x35;
1525         *pbuffer++ = 0xff;
1526         *pbuffer++ = 0xff;
1527         *pbuffer++ = 0xfe;
1528
1529         if (info->AsicID == ELECTRABUZZ_ID) {
1530                 for (i = 0; i < len / 2; i++) {
1531                         tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO);
1532                         *pbuffer++ = (u8) (tempword >> 8);
1533                         *pbuffer++ = (u8)tempword;
1534                         if (ft1000_chkcard(dev) == false) {
1535                                 kfree_skb(skb);
1536                                 return FAILURE;
1537                         }
1538                 }
1539
1540                 /* Need to read one more word if odd byte */
1541                 if (len & 0x0001) {
1542                         tempword = ft1000_read_reg(dev, FT1000_REG_DFIFO);
1543                         *pbuffer++ = (u8) (tempword >> 8);
1544                 }
1545         } else {
1546                 ptemplong = (u32 *)pbuffer;
1547                 for (i = 0; i < len / 4; i++) {
1548                         templong = inl(dev->base_addr + FT1000_REG_MAG_DFR);
1549                         pr_debug("Data = 0x%8x\n", templong);
1550                         *ptemplong++ = templong;
1551                 }
1552
1553                 /* Need to read one more word if odd align. */
1554                 if (len & 0x0003) {
1555                         templong = inl(dev->base_addr + FT1000_REG_MAG_DFR);
1556                         pr_debug("Data = 0x%8x\n", templong);
1557                         *ptemplong++ = templong;
1558                 }
1559
1560         }
1561
1562         pr_debug("Data passed to Protocol layer:\n");
1563         for (i = 0; i < len + 12; i++)
1564                 pr_debug("Protocol Data: 0x%x\n", *ptemp++);
1565
1566         skb->dev = dev;
1567         skb->protocol = eth_type_trans(skb, dev);
1568         skb->ip_summed = CHECKSUM_UNNECESSARY;
1569         netif_rx(skb);
1570
1571         info->stats.rx_packets++;
1572         /* Add on 12 bytes for MAC address which was removed */
1573         info->stats.rx_bytes += (len + 12);
1574
1575         if (info->AsicID == ELECTRABUZZ_ID) {
1576                 /* track how many bytes have been read from FIFO - round up to
1577                  * 16 bit word */
1578                 tempword = len + 16;
1579                 if (tempword & 0x01)
1580                         tempword++;
1581                 info->fifo_cnt += tempword;
1582                 ft1000_write_reg(dev, FT1000_REG_DPRAM_ADDR, FT1000_FIFO_LEN);
1583                 ft1000_write_reg(dev, FT1000_REG_DPRAM_DATA, info->fifo_cnt);
1584         }
1585
1586         return SUCCESS;
1587 }
1588
1589 /*---------------------------------------------------------------------------
1590
1591   Function:   ft1000_copy_down_pkt
1592   Description: This function will take an ethernet packet and convert it to
1593   a Flarion packet prior to sending it to the ASIC Downlink
1594   FIFO.
1595   Input:
1596   dev    - device structure
1597   packet - address of ethernet packet
1598   len    - length of IP packet
1599   Output:
1600   status - FAILURE
1601   SUCCESS
1602
1603   -------------------------------------------------------------------------*/
1604 static int ft1000_copy_down_pkt(struct net_device *dev, u16 *packet, u16 len)
1605 {
1606         struct ft1000_info *info = netdev_priv(dev);
1607         struct ft1000_pcmcia *pcmcia = info->priv;
1608         union {
1609                 struct pseudo_hdr blk;
1610                 u16 buff[sizeof(struct pseudo_hdr) >> 1];
1611                 u8 buffc[sizeof(struct pseudo_hdr)];
1612         } pseudo;
1613         int i;
1614         u32 *plong;
1615
1616         /* Check if there is room on the FIFO */
1617         if (len > ft1000_read_fifo_len(dev)) {
1618                 udelay(10);
1619                 if (len > ft1000_read_fifo_len(dev))
1620                         udelay(20);
1621                 if (len > ft1000_read_fifo_len(dev))
1622                         udelay(20);
1623                 if (len > ft1000_read_fifo_len(dev))
1624                         udelay(20);
1625                 if (len > ft1000_read_fifo_len(dev))
1626                         udelay(20);
1627                 if (len > ft1000_read_fifo_len(dev))
1628                         udelay(20);
1629                 if (len > ft1000_read_fifo_len(dev)) {
1630                         pr_debug("Transmit FIFO is full - pkt drop\n");
1631                         info->stats.tx_errors++;
1632                         return SUCCESS;
1633                 }
1634         }
1635         /* Create pseudo header and send pseudo/ip to hardware */
1636         if (info->AsicID == ELECTRABUZZ_ID)
1637                 pseudo.blk.length = len;
1638         else
1639                 pseudo.blk.length = ntohs(len);
1640
1641         pseudo.blk.source = DSPID;      /* Need to swap to get in correct
1642                                            order */
1643         pseudo.blk.destination = HOSTID;
1644         pseudo.blk.portdest = NETWORKID;        /* Need to swap to get in
1645                                                    correct order */
1646         pseudo.blk.portsrc = DSPAIRID;
1647         pseudo.blk.sh_str_id = 0;
1648         pseudo.blk.control = 0;
1649         pseudo.blk.rsvd1 = 0;
1650         pseudo.blk.seq_num = 0;
1651         pseudo.blk.rsvd2 = pcmcia->packetseqnum++;
1652         pseudo.blk.qos_class = 0;
1653         /* Calculate pseudo header checksum */
1654         pseudo.blk.checksum = pseudo.buff[0];
1655         for (i = 1; i < 7; i++)
1656                 pseudo.blk.checksum ^= pseudo.buff[i];
1657
1658         /* Production Mode */
1659         if (info->AsicID == ELECTRABUZZ_ID) {
1660                 /* copy first word to UFIFO_BEG reg */
1661                 ft1000_write_reg(dev, FT1000_REG_UFIFO_BEG, pseudo.buff[0]);
1662                 pr_debug("data 0 BEG = 0x%04x\n", pseudo.buff[0]);
1663
1664                 /* copy subsequent words to UFIFO_MID reg */
1665                 ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[1]);
1666                 pr_debug("data 1 MID = 0x%04x\n", pseudo.buff[1]);
1667                 ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[2]);
1668                 pr_debug("data 2 MID = 0x%04x\n", pseudo.buff[2]);
1669                 ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[3]);
1670                 pr_debug("data 3 MID = 0x%04x\n", pseudo.buff[3]);
1671                 ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[4]);
1672                 pr_debug("data 4 MID = 0x%04x\n", pseudo.buff[4]);
1673                 ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[5]);
1674                 pr_debug("data 5 MID = 0x%04x\n", pseudo.buff[5]);
1675                 ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[6]);
1676                 pr_debug("data 6 MID = 0x%04x\n", pseudo.buff[6]);
1677                 ft1000_write_reg(dev, FT1000_REG_UFIFO_MID, pseudo.buff[7]);
1678                 pr_debug("data 7 MID = 0x%04x\n", pseudo.buff[7]);
1679
1680                 /* Write PPP type + IP Packet into Downlink FIFO */
1681                 for (i = 0; i < (len >> 1) - 1; i++) {
1682                         ft1000_write_reg(dev, FT1000_REG_UFIFO_MID,
1683                                          htons(*packet));
1684                         pr_debug("data %d MID = 0x%04x\n",
1685                                  i + 8, htons(*packet));
1686                         packet++;
1687                 }
1688
1689                 /* Check for odd byte */
1690                 if (len & 0x0001) {
1691                         ft1000_write_reg(dev, FT1000_REG_UFIFO_MID,
1692                                          htons(*packet));
1693                         pr_debug("data MID = 0x%04x\n", htons(*packet));
1694                         packet++;
1695                         ft1000_write_reg(dev, FT1000_REG_UFIFO_END,
1696                                          htons(*packet));
1697                         pr_debug("data %d MID = 0x%04x\n",
1698                                  i + 8, htons(*packet));
1699                 } else {
1700                         ft1000_write_reg(dev, FT1000_REG_UFIFO_END,
1701                                          htons(*packet));
1702                         pr_debug("data %d MID = 0x%04x\n",
1703                                  i + 8, htons(*packet));
1704                 }
1705         } else {
1706                 outl(*(u32 *)&pseudo.buff[0],
1707                      dev->base_addr + FT1000_REG_MAG_UFDR);
1708                 pr_debug("Pseudo = 0x%8x\n", *(u32 *)&pseudo.buff[0]);
1709                 outl(*(u32 *)&pseudo.buff[2],
1710                      dev->base_addr + FT1000_REG_MAG_UFDR);
1711                 pr_debug("Pseudo = 0x%8x\n", *(u32 *)&pseudo.buff[2]);
1712                 outl(*(u32 *)&pseudo.buff[4],
1713                      dev->base_addr + FT1000_REG_MAG_UFDR);
1714                 pr_debug("Pseudo = 0x%8x\n", *(u32 *)&pseudo.buff[4]);
1715                 outl(*(u32 *)&pseudo.buff[6],
1716                      dev->base_addr + FT1000_REG_MAG_UFDR);
1717                 pr_debug("Pseudo = 0x%8x\n", *(u32 *)&pseudo.buff[6]);
1718
1719                 plong = (u32 *)packet;
1720                 /* Write PPP type + IP Packet into Downlink FIFO */
1721                 for (i = 0; i < (len >> 2); i++)
1722                         outl(*plong++, dev->base_addr + FT1000_REG_MAG_UFDR);
1723
1724                 /* Check for odd alignment */
1725                 if (len & 0x0003) {
1726                         pr_debug("data = 0x%8x\n", *plong);
1727                         outl(*plong++, dev->base_addr + FT1000_REG_MAG_UFDR);
1728                 }
1729                 outl(1, dev->base_addr + FT1000_REG_MAG_UFER);
1730         }
1731
1732         info->stats.tx_packets++;
1733         /* Add 14 bytes for MAC address plus ethernet type */
1734         info->stats.tx_bytes += (len + 14);
1735         return SUCCESS;
1736 }
1737
1738 static struct net_device_stats *ft1000_stats(struct net_device *dev)
1739 {
1740         struct ft1000_info *info = netdev_priv(dev);
1741
1742         return &info->stats;
1743 }
1744
1745 static int ft1000_open(struct net_device *dev)
1746 {
1747         ft1000_reset_card(dev);
1748
1749         /* schedule ft1000_hbchk to perform periodic heartbeat checks on DSP
1750          * and ASIC */
1751         init_timer(&poll_timer);
1752         poll_timer.expires = jiffies + (2 * HZ);
1753         poll_timer.data = (u_long)dev;
1754         add_timer(&poll_timer);
1755
1756         return 0;
1757 }
1758
1759 static int ft1000_close(struct net_device *dev)
1760 {
1761         struct ft1000_info *info = netdev_priv(dev);
1762
1763         info->CardReady = 0;
1764         del_timer(&poll_timer);
1765
1766         if (ft1000_card_present == 1) {
1767                 pr_debug("Media is down\n");
1768                 netif_stop_queue(dev);
1769
1770                 ft1000_disable_interrupts(dev);
1771                 ft1000_write_reg(dev, FT1000_REG_RESET, DSP_RESET_BIT);
1772
1773                 /* reset ASIC */
1774                 ft1000_reset_asic(dev);
1775         }
1776         return 0;
1777 }
1778
1779 static int ft1000_start_xmit(struct sk_buff *skb, struct net_device *dev)
1780 {
1781         struct ft1000_info *info = netdev_priv(dev);
1782         u8 *pdata;
1783
1784         if (skb == NULL) {
1785                 pr_debug("skb == NULL!!!\n");
1786                 return 0;
1787         }
1788
1789         pr_debug("length of packet = %d\n", skb->len);
1790
1791         pdata = (u8 *)skb->data;
1792
1793         if (info->mediastate == 0) {
1794                 /* Drop packet is mediastate is down */
1795                 pr_debug("mediastate is down\n");
1796                 return SUCCESS;
1797         }
1798
1799         if ((skb->len < ENET_HEADER_SIZE) || (skb->len > ENET_MAX_SIZE)) {
1800                 /* Drop packet which has invalid size */
1801                 pr_debug("invalid ethernet length\n");
1802                 return SUCCESS;
1803         }
1804         ft1000_copy_down_pkt(dev, (u16 *) (pdata + ENET_HEADER_SIZE - 2),
1805                              skb->len - ENET_HEADER_SIZE + 2);
1806
1807         dev_kfree_skb(skb);
1808
1809         return 0;
1810 }
1811
1812 static irqreturn_t ft1000_interrupt(int irq, void *dev_id)
1813 {
1814         struct net_device *dev = dev_id;
1815         struct ft1000_info *info = netdev_priv(dev);
1816         u16 tempword;
1817         u16 inttype;
1818         int cnt;
1819
1820         if (info->CardReady == 0) {
1821                 ft1000_disable_interrupts(dev);
1822                 return IRQ_HANDLED;
1823         }
1824
1825         if (ft1000_chkcard(dev) == false) {
1826                 ft1000_disable_interrupts(dev);
1827                 return IRQ_HANDLED;
1828         }
1829
1830         ft1000_disable_interrupts(dev);
1831
1832         /* Read interrupt type */
1833         inttype = ft1000_read_reg(dev, FT1000_REG_SUP_ISR);
1834
1835         /* Make sure we process all interrupt before leaving the ISR due to the
1836          * edge trigger interrupt type */
1837         while (inttype) {
1838                 if (inttype & ISR_DOORBELL_PEND)
1839                         ft1000_parse_dpram_msg(dev);
1840
1841                 if (inttype & ISR_RCV) {
1842                         pr_debug("Data in FIFO\n");
1843
1844                         cnt = 0;
1845                         do {
1846                                 /* Check if we have packets in the Downlink
1847                                  * FIFO */
1848                                 if (info->AsicID == ELECTRABUZZ_ID) {
1849                                         tempword = ft1000_read_reg(dev,
1850                                                         FT1000_REG_DFIFO_STAT);
1851                                 } else {
1852                                         tempword = ft1000_read_reg(dev,
1853                                                         FT1000_REG_MAG_DFSR);
1854                                 }
1855                                 if (!(tempword & 0x1f))
1856                                         break;
1857                                 ft1000_copy_up_pkt(dev);
1858                                 cnt++;
1859                         } while (cnt < MAX_RCV_LOOP);
1860
1861                 }
1862                 /* clear interrupts */
1863                 tempword = ft1000_read_reg(dev, FT1000_REG_SUP_ISR);
1864                 pr_debug("interrupt status register = 0x%x\n", tempword);
1865                 ft1000_write_reg(dev, FT1000_REG_SUP_ISR, tempword);
1866
1867                 /* Read interrupt type */
1868                 inttype = ft1000_read_reg(dev, FT1000_REG_SUP_ISR);
1869                 pr_debug("interrupt status register after clear = 0x%x\n",
1870                          inttype);
1871         }
1872         ft1000_enable_interrupts(dev);
1873         return IRQ_HANDLED;
1874 }
1875
1876 void stop_ft1000_card(struct net_device *dev)
1877 {
1878         struct ft1000_info *info = netdev_priv(dev);
1879         struct prov_record *ptr;
1880         struct prov_record *tmp;
1881         /* int cnt; */
1882
1883         info->CardReady = 0;
1884         ft1000_card_present = 0;
1885         netif_stop_queue(dev);
1886         ft1000_disable_interrupts(dev);
1887
1888         /* Make sure we free any memory reserve for provisioning */
1889         list_for_each_entry_safe(ptr, tmp, &info->prov_list, list) {
1890                 list_del(&ptr->list);
1891                 kfree(ptr->pprov_data);
1892                 kfree(ptr);
1893         }
1894
1895         kfree(info->priv);
1896
1897         if (info->registered) {
1898                 unregister_netdev(dev);
1899                 info->registered = 0;
1900         }
1901
1902         free_irq(dev->irq, dev);
1903         release_region(dev->base_addr, 256);
1904         release_firmware(fw_entry);
1905         flarion_ft1000_cnt--;
1906
1907 }
1908
1909 static void ft1000_get_drvinfo(struct net_device *dev,
1910                                struct ethtool_drvinfo *info)
1911 {
1912         struct ft1000_info *ft_info;
1913
1914         ft_info = netdev_priv(dev);
1915
1916         strlcpy(info->driver, "ft1000", sizeof(info->driver));
1917         snprintf(info->bus_info, sizeof(info->bus_info), "PCMCIA 0x%lx",
1918                  dev->base_addr);
1919         snprintf(info->fw_version, sizeof(info->fw_version), "%d.%d.%d.%d",
1920                  ft_info->DspVer[0], ft_info->DspVer[1], ft_info->DspVer[2],
1921                  ft_info->DspVer[3]);
1922 }
1923
1924 static u32 ft1000_get_link(struct net_device *dev)
1925 {
1926         struct ft1000_info *info;
1927
1928         info = netdev_priv(dev);
1929         return info->mediastate;
1930 }
1931
1932 static const struct ethtool_ops ops = {
1933         .get_drvinfo = ft1000_get_drvinfo,
1934         .get_link = ft1000_get_link
1935 };
1936
1937 struct net_device *init_ft1000_card(struct pcmcia_device *link,
1938                                     void *ft1000_reset)
1939 {
1940         struct ft1000_info *info;
1941         struct ft1000_pcmcia *pcmcia;
1942         struct net_device *dev;
1943
1944         static const struct net_device_ops ft1000ops = {
1945                         .ndo_open = &ft1000_open,
1946                         .ndo_stop = &ft1000_close,
1947                         .ndo_start_xmit = &ft1000_start_xmit,
1948                         .ndo_get_stats = &ft1000_stats,
1949                 };
1950
1951         pr_debug("irq = %d, port = 0x%04llx\n",
1952                  link->irq, (unsigned long long)link->resource[0]->start);
1953
1954         flarion_ft1000_cnt++;
1955
1956         if (flarion_ft1000_cnt > 1) {
1957                 flarion_ft1000_cnt--;
1958
1959                 dev_info(&link->dev,
1960                          "This driver can not support more than one instance\n");
1961                 return NULL;
1962         }
1963
1964         dev = alloc_etherdev(sizeof(struct ft1000_info));
1965         if (!dev) {
1966                 dev_err(&link->dev, "Failed to allocate etherdev\n");
1967                 return NULL;
1968         }
1969
1970         SET_NETDEV_DEV(dev, &link->dev);
1971         info = netdev_priv(dev);
1972
1973         memset(info, 0, sizeof(struct ft1000_info));
1974
1975         pr_debug("address of dev = 0x%p\n", dev);
1976         pr_debug("address of dev info = 0x%p\n", info);
1977         pr_debug("device name = %s\n", dev->name);
1978
1979         memset(&info->stats, 0, sizeof(struct net_device_stats));
1980
1981         info->priv = kzalloc(sizeof(struct ft1000_pcmcia), GFP_KERNEL);
1982         pcmcia = info->priv;
1983         pcmcia->link = link;
1984
1985         spin_lock_init(&info->dpram_lock);
1986         info->DrvErrNum = 0;
1987         info->registered = 1;
1988         info->ft1000_reset = ft1000_reset;
1989         info->mediastate = 0;
1990         info->fifo_cnt = 0;
1991         info->CardReady = 0;
1992         info->DSP_TIME[0] = 0;
1993         info->DSP_TIME[1] = 0;
1994         info->DSP_TIME[2] = 0;
1995         info->DSP_TIME[3] = 0;
1996         flarion_ft1000_cnt = 0;
1997
1998         INIT_LIST_HEAD(&info->prov_list);
1999
2000         info->squeseqnum = 0;
2001
2002         /* dev->hard_start_xmit = &ft1000_start_xmit; */
2003         /* dev->get_stats = &ft1000_stats; */
2004         /* dev->open = &ft1000_open; */
2005         /* dev->stop = &ft1000_close; */
2006
2007         dev->netdev_ops = &ft1000ops;
2008
2009         pr_debug("device name = %s\n", dev->name);
2010
2011         dev->irq = link->irq;
2012         dev->base_addr = link->resource[0]->start;
2013         if (pcmcia_get_mac_from_cis(link, dev)) {
2014                 netdev_err(dev, "Could not read mac address\n");
2015                 goto err_dev;
2016         }
2017
2018         if (request_irq(dev->irq, ft1000_interrupt, IRQF_SHARED, dev->name,
2019                         dev)) {
2020                 netdev_err(dev, "Could not request_irq\n");
2021                 goto err_dev;
2022         }
2023
2024         if (request_region(dev->base_addr, 256, dev->name) == NULL) {
2025                 netdev_err(dev, "Could not request_region\n");
2026                 goto err_irq;
2027         }
2028
2029         if (register_netdev(dev)) {
2030                 pr_debug("Could not register netdev\n");
2031                 goto err_reg;
2032         }
2033
2034         info->AsicID = ft1000_read_reg(dev, FT1000_REG_ASIC_ID);
2035         if (info->AsicID == ELECTRABUZZ_ID) {
2036                 pr_debug("ELECTRABUZZ ASIC\n");
2037                 if (request_firmware(&fw_entry, "ft1000.img",
2038                                      &link->dev) != 0) {
2039                         pr_info("Could not open ft1000.img\n");
2040                         goto err_unreg;
2041                 }
2042         } else {
2043                 pr_debug("MAGNEMITE ASIC\n");
2044                 if (request_firmware(&fw_entry, "ft2000.img",
2045                                      &link->dev) != 0) {
2046                         pr_info("Could not open ft2000.img\n");
2047                         goto err_unreg;
2048                 }
2049         }
2050
2051         ft1000_enable_interrupts(dev);
2052
2053         ft1000_card_present = 1;
2054         dev->ethtool_ops = &ops;
2055         pr_info("%s: addr 0x%04lx irq %d, MAC addr %pM\n",
2056                 dev->name, dev->base_addr, dev->irq, dev->dev_addr);
2057         return dev;
2058
2059 err_unreg:
2060         unregister_netdev(dev);
2061 err_reg:
2062         release_region(dev->base_addr, 256);
2063 err_irq:
2064         free_irq(dev->irq, dev);
2065 err_dev:
2066         free_netdev(dev);
2067         return NULL;
2068 }