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