]> git.proxmox.com Git - mirror_ubuntu-bionic-kernel.git/blame - drivers/staging/slicoss/slicoss.c
Staging: slicoss: remove DBG_MSG
[mirror_ubuntu-bionic-kernel.git] / drivers / staging / slicoss / slicoss.c
CommitLineData
4d6f6af8
GKH
1/**************************************************************************
2 *
3 * Copyright 2000-2006 Alacritech, Inc. All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 *
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above
12 * copyright notice, this list of conditions and the following
13 * disclaimer in the documentation and/or other materials provided
14 * with the distribution.
15 *
16 * Alternatively, this software may be distributed under the terms of the
17 * GNU General Public License ("GPL") version 2 as published by the Free
18 * Software Foundation.
19 *
20 * THIS SOFTWARE IS PROVIDED BY ALACRITECH, INC. ``AS IS'' AND ANY
21 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
22 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
23 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL ALACRITECH, INC. OR
24 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
25 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
26 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF
27 * USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
28 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
29 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
30 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31 * SUCH DAMAGE.
32 *
33 * The views and conclusions contained in the software and documentation
34 * are those of the authors and should not be interpreted as representing
35 * official policies, either expressed or implied, of Alacritech, Inc.
36 *
37 **************************************************************************/
38
39/*
40 * FILENAME: slicoss.c
41 *
42 * The SLICOSS driver for Alacritech's IS-NIC products.
43 *
44 * This driver is supposed to support:
45 *
46 * Mojave cards (single port PCI Gigabit) both copper and fiber
47 * Oasis cards (single and dual port PCI-x Gigabit) copper and fiber
48 * Kalahari cards (dual and quad port PCI-e Gigabit) copper and fiber
49 *
50 * The driver was acutally tested on Oasis and Kalahari cards.
51 *
52 *
53 * NOTE: This is the standard, non-accelerated version of Alacritech's
54 * IS-NIC driver.
55 */
56
4d6f6af8 57
4d6f6af8
GKH
58#define KLUDGE_FOR_4GB_BOUNDARY 1
59#define DEBUG_MICROCODE 1
4d6f6af8
GKH
60#define DBG 1
61#define SLIC_ASSERT_ENABLED 1
4d6f6af8 62#define SLIC_INTERRUPT_PROCESS_LIMIT 1
4d6f6af8
GKH
63#define SLIC_OFFLOAD_IP_CHECKSUM 1
64#define STATS_TIMER_INTERVAL 2
65#define PING_TIMER_INTERVAL 1
66
67#include <linux/kernel.h>
68#include <linux/string.h>
69#include <linux/errno.h>
70#include <linux/ioport.h>
71#include <linux/slab.h>
72#include <linux/interrupt.h>
73#include <linux/timer.h>
74#include <linux/pci.h>
75#include <linux/spinlock.h>
76#include <linux/init.h>
77#include <linux/bitops.h>
78#include <linux/io.h>
79#include <linux/netdevice.h>
80#include <linux/etherdevice.h>
81#include <linux/skbuff.h>
82#include <linux/delay.h>
83#include <linux/debugfs.h>
84#include <linux/seq_file.h>
85#include <linux/kthread.h>
86#include <linux/module.h>
87#include <linux/moduleparam.h>
88
470c5736 89#include <linux/firmware.h>
4d6f6af8 90#include <linux/types.h>
4d6f6af8 91#include <linux/dma-mapping.h>
4d6f6af8
GKH
92#include <linux/mii.h>
93#include <linux/if_vlan.h>
4d6f6af8
GKH
94#include <asm/unaligned.h>
95
96#include <linux/ethtool.h>
97#define SLIC_ETHTOOL_SUPPORT 1
98
99#include <linux/uaccess.h>
77faefa3
GKH
100#include "slicdbg.h"
101#include "slichw.h"
102#include "slic.h"
103
77faefa3 104static struct net_device_stats *slic_get_stats(struct net_device *dev);
77faefa3
GKH
105static int slic_entry_open(struct net_device *dev);
106static int slic_entry_halt(struct net_device *dev);
107static int slic_ioctl(struct net_device *dev, struct ifreq *rq, int cmd);
108static int slic_xmit_start(struct sk_buff *skb, struct net_device *dev);
109static void slic_xmit_fail(struct adapter *adapter, struct sk_buff *skb,
110 void *cmd, u32 skbtype, u32 status);
111static void slic_config_pci(struct pci_dev *pcidev);
112static struct sk_buff *slic_rcvqueue_getnext(struct adapter *adapter);
113static int slic_mac_set_address(struct net_device *dev, void *ptr);
114static void slic_link_event_handler(struct adapter *adapter);
115static void slic_upr_request_complete(struct adapter *adapter, u32 isr);
116static int slic_rspqueue_init(struct adapter *adapter);
77faefa3
GKH
117static void slic_rspqueue_free(struct adapter *adapter);
118static struct slic_rspbuf *slic_rspqueue_getnext(struct adapter *adapter);
119static int slic_cmdq_init(struct adapter *adapter);
120static void slic_cmdq_free(struct adapter *adapter);
121static void slic_cmdq_reset(struct adapter *adapter);
122static void slic_cmdq_addcmdpage(struct adapter *adapter, u32 *page);
123static void slic_cmdq_getdone(struct adapter *adapter);
124static void slic_cmdq_putdone_irq(struct adapter *adapter,
125 struct slic_hostcmd *cmd);
126static struct slic_hostcmd *slic_cmdq_getfree(struct adapter *adapter);
127static int slic_rcvqueue_init(struct adapter *adapter);
77faefa3
GKH
128static int slic_rcvqueue_fill(struct adapter *adapter);
129static u32 slic_rcvqueue_reinsert(struct adapter *adapter, struct sk_buff *skb);
130static void slic_rcvqueue_free(struct adapter *adapter);
131static void slic_adapter_set_hwaddr(struct adapter *adapter);
132static int slic_card_init(struct sliccard *card, struct adapter *adapter);
133static void slic_intagg_set(struct adapter *adapter, u32 value);
134static int slic_card_download(struct adapter *adapter);
135static u32 slic_card_locate(struct adapter *adapter);
136static int slic_if_init(struct adapter *adapter);
137static int slic_adapter_allocresources(struct adapter *adapter);
138static void slic_adapter_freeresources(struct adapter *adapter);
139static void slic_link_config(struct adapter *adapter, u32 linkspeed,
140 u32 linkduplex);
141static void slic_unmap_mmio_space(struct adapter *adapter);
142static void slic_card_cleanup(struct sliccard *card);
143static void slic_soft_reset(struct adapter *adapter);
144static bool slic_mac_filter(struct adapter *adapter,
145 struct ether_header *ether_frame);
146static void slic_mac_address_config(struct adapter *adapter);
147static void slic_mac_config(struct adapter *adapter);
148static void slic_mcast_set_mask(struct adapter *adapter);
149static void slic_config_set(struct adapter *adapter, bool linkchange);
150static void slic_config_clear(struct adapter *adapter);
151static void slic_config_get(struct adapter *adapter, u32 config,
152 u32 configh);
153static void slic_timer_load_check(ulong context);
154static void slic_assert_fail(void);
155static ushort slic_eeprom_cksum(char *m, int len);
156static void slic_upr_start(struct adapter *adapter);
157static void slic_link_upr_complete(struct adapter *adapter, u32 Isr);
158static int slic_upr_request(struct adapter *adapter, u32 upr_request,
159 u32 upr_data, u32 upr_data_h, u32 upr_buffer,
160 u32 upr_buffer_h);
161static void slic_mcast_set_list(struct net_device *dev);
162
4d6f6af8 163
4d6f6af8
GKH
164static uint slic_first_init = 1;
165static char *slic_banner = "Alacritech SLIC Technology(tm) Server "\
e9ef456e 166 "and Storage Accelerator (Non-Accelerated)";
4d6f6af8
GKH
167
168static char *slic_proc_version = "2.0.351 2006/07/14 12:26:00";
169static char *slic_product_name = "SLIC Technology(tm) Server "\
170 "and Storage Accelerator (Non-Accelerated)";
171static char *slic_vendor = "Alacritech, Inc.";
172
173static int slic_debug = 1;
174static int debug = -1;
175static struct net_device *head_netdevice;
176
e9eff9d6 177static struct base_driver slic_global = { {}, 0, 0, 0, 1, NULL, NULL };
4d6f6af8
GKH
178static int intagg_delay = 100;
179static u32 dynamic_intagg;
4d6f6af8
GKH
180static unsigned int rcv_count;
181static struct dentry *slic_debugfs;
182
183#define DRV_NAME "slicoss"
184#define DRV_VERSION "2.0.1"
185#define DRV_AUTHOR "Alacritech, Inc. Engineering"
186#define DRV_DESCRIPTION "Alacritech SLIC Techonology(tm) "\
187 "Non-Accelerated Driver"
188#define DRV_COPYRIGHT "Copyright 2000-2006 Alacritech, Inc. "\
189 "All rights reserved."
190#define PFX DRV_NAME " "
191
192MODULE_AUTHOR(DRV_AUTHOR);
193MODULE_DESCRIPTION(DRV_DESCRIPTION);
194MODULE_LICENSE("Dual BSD/GPL");
195
196module_param(dynamic_intagg, int, 0);
197MODULE_PARM_DESC(dynamic_intagg, "Dynamic Interrupt Aggregation Setting");
198module_param(intagg_delay, int, 0);
199MODULE_PARM_DESC(intagg_delay, "uSec Interrupt Aggregation Delay");
200
201static struct pci_device_id slic_pci_tbl[] __devinitdata = {
202 {PCI_VENDOR_ID_ALACRITECH,
203 SLIC_1GB_DEVICE_ID,
204 PCI_ANY_ID, PCI_ANY_ID,},
205 {PCI_VENDOR_ID_ALACRITECH,
206 SLIC_2GB_DEVICE_ID,
207 PCI_ANY_ID, PCI_ANY_ID,},
208 {0,}
209};
210
211MODULE_DEVICE_TABLE(pci, slic_pci_tbl);
212
213#define SLIC_GET_SLIC_HANDLE(_adapter, _pslic_handle) \
214{ \
e9eff9d6
LD
215 spin_lock_irqsave(&_adapter->handle_lock.lock, \
216 _adapter->handle_lock.flags); \
4d6f6af8
GKH
217 _pslic_handle = _adapter->pfree_slic_handles; \
218 if (_pslic_handle) { \
219 ASSERT(_pslic_handle->type == SLIC_HANDLE_FREE); \
220 _adapter->pfree_slic_handles = _pslic_handle->next; \
221 } \
e9eff9d6
LD
222 spin_unlock_irqrestore(&_adapter->handle_lock.lock, \
223 _adapter->handle_lock.flags); \
4d6f6af8
GKH
224}
225
226#define SLIC_FREE_SLIC_HANDLE(_adapter, _pslic_handle) \
227{ \
228 _pslic_handle->type = SLIC_HANDLE_FREE; \
e9eff9d6
LD
229 spin_lock_irqsave(&_adapter->handle_lock.lock, \
230 _adapter->handle_lock.flags); \
4d6f6af8
GKH
231 _pslic_handle->next = _adapter->pfree_slic_handles; \
232 _adapter->pfree_slic_handles = _pslic_handle; \
e9eff9d6
LD
233 spin_unlock_irqrestore(&_adapter->handle_lock.lock, \
234 _adapter->handle_lock.flags); \
4d6f6af8
GKH
235}
236
237static void slic_debug_init(void);
238static void slic_debug_cleanup(void);
e9eff9d6
LD
239static void slic_debug_adapter_create(struct adapter *adapter);
240static void slic_debug_adapter_destroy(struct adapter *adapter);
241static void slic_debug_card_create(struct sliccard *card);
242static void slic_debug_card_destroy(struct sliccard *card);
4d6f6af8 243
62f691a3 244static inline void slic_reg32_write(void __iomem *reg, u32 value, bool flush)
4d6f6af8
GKH
245{
246 writel(value, reg);
247 if (flush)
248 mb();
249}
250
28980a3c
GKH
251static inline void slic_reg64_write(struct adapter *adapter, void __iomem *reg,
252 u32 value, void __iomem *regh, u32 paddrh,
253 bool flush)
4d6f6af8 254{
e9eff9d6
LD
255 spin_lock_irqsave(&adapter->bit64reglock.lock,
256 adapter->bit64reglock.flags);
4d6f6af8
GKH
257 if (paddrh != adapter->curaddrupper) {
258 adapter->curaddrupper = paddrh;
259 writel(paddrh, regh);
260 }
261 writel(value, reg);
262 if (flush)
263 mb();
e9eff9d6
LD
264 spin_unlock_irqrestore(&adapter->bit64reglock.lock,
265 adapter->bit64reglock.flags);
4d6f6af8
GKH
266}
267
e9eff9d6 268static void slic_init_driver(void)
4d6f6af8
GKH
269{
270 if (slic_first_init) {
4d6f6af8 271 slic_first_init = 0;
e9eff9d6 272 spin_lock_init(&slic_global.driver_lock.lock);
4d6f6af8
GKH
273 slic_debug_init();
274 }
275}
276
4d6f6af8
GKH
277static void slic_init_adapter(struct net_device *netdev,
278 struct pci_dev *pcidev,
279 const struct pci_device_id *pci_tbl_entry,
280 void __iomem *memaddr, int chip_idx)
281{
282 ushort index;
e9eff9d6
LD
283 struct slic_handle *pslic_handle;
284 struct adapter *adapter = (struct adapter *)netdev_priv(netdev);
e8bc9b7a 285
4d6f6af8
GKH
286/* adapter->pcidev = pcidev;*/
287 adapter->vendid = pci_tbl_entry->vendor;
288 adapter->devid = pci_tbl_entry->device;
289 adapter->subsysid = pci_tbl_entry->subdevice;
290 adapter->busnumber = pcidev->bus->number;
291 adapter->slotnumber = ((pcidev->devfn >> 3) & 0x1F);
292 adapter->functionnumber = (pcidev->devfn & 0x7);
293 adapter->memorylength = pci_resource_len(pcidev, 0);
e9eff9d6 294 adapter->slic_regs = (__iomem struct slic_regs *)memaddr;
4d6f6af8
GKH
295 adapter->irq = pcidev->irq;
296/* adapter->netdev = netdev;*/
297 adapter->next_netdevice = head_netdevice;
298 head_netdevice = netdev;
299 adapter->chipid = chip_idx;
300 adapter->port = 0; /*adapter->functionnumber;*/
301 adapter->cardindex = adapter->port;
302 adapter->memorybase = memaddr;
e9eff9d6
LD
303 spin_lock_init(&adapter->upr_lock.lock);
304 spin_lock_init(&adapter->bit64reglock.lock);
305 spin_lock_init(&adapter->adapter_lock.lock);
306 spin_lock_init(&adapter->reset_lock.lock);
307 spin_lock_init(&adapter->handle_lock.lock);
4d6f6af8
GKH
308
309 adapter->card_size = 1;
310 /*
311 Initialize slic_handle array
312 */
313 ASSERT(SLIC_CMDQ_MAXCMDS <= 0xFFFF);
314 /*
315 Start with 1. 0 is an invalid host handle.
316 */
317 for (index = 1, pslic_handle = &adapter->slic_handles[1];
318 index < SLIC_CMDQ_MAXCMDS; index++, pslic_handle++) {
319
320 pslic_handle->token.handle_index = index;
321 pslic_handle->type = SLIC_HANDLE_FREE;
322 pslic_handle->next = adapter->pfree_slic_handles;
323 adapter->pfree_slic_handles = pslic_handle;
324 }
e9eff9d6
LD
325 adapter->pshmem = (struct slic_shmem *)
326 pci_alloc_consistent(adapter->pcidev,
66615321 327 sizeof(struct slic_shmem),
e9eff9d6
LD
328 &adapter->
329 phys_shmem);
4d6f6af8
GKH
330 ASSERT(adapter->pshmem);
331
e9eff9d6 332 memset(adapter->pshmem, 0, sizeof(struct slic_shmem));
4d6f6af8
GKH
333
334 return;
335}
336
e9eff9d6 337static int __devinit slic_entry_probe(struct pci_dev *pcidev,
4d6f6af8
GKH
338 const struct pci_device_id *pci_tbl_entry)
339{
340 static int cards_found;
341 static int did_version;
1025744a 342 int err = -ENODEV;
4d6f6af8 343 struct net_device *netdev;
e9eff9d6 344 struct adapter *adapter;
4d6f6af8 345 void __iomem *memmapped_ioaddr = NULL;
e9eff9d6 346 u32 status = 0;
4d6f6af8
GKH
347 ulong mmio_start = 0;
348 ulong mmio_len = 0;
e9eff9d6 349 struct sliccard *card = NULL;
4d6f6af8 350
4d6f6af8
GKH
351 slic_global.dynamic_intagg = dynamic_intagg;
352
353 err = pci_enable_device(pcidev);
354
4d6f6af8
GKH
355 if (err)
356 return err;
357
358 if (slic_debug > 0 && did_version++ == 0) {
e9ef456e
GKH
359 printk(KERN_DEBUG "%s\n", slic_banner);
360 printk(KERN_DEBUG "%s\n", slic_proc_version);
4d6f6af8
GKH
361 }
362
363 err = pci_set_dma_mask(pcidev, DMA_64BIT_MASK);
e8bc9b7a 364 if (err) {
4d6f6af8 365 err = pci_set_dma_mask(pcidev, DMA_32BIT_MASK);
e8bc9b7a 366 if (err)
1025744a 367 goto err_out_disable_pci;
4d6f6af8
GKH
368 }
369
4d6f6af8 370 err = pci_request_regions(pcidev, DRV_NAME);
e8bc9b7a 371 if (err)
1025744a 372 goto err_out_disable_pci;
4d6f6af8 373
4d6f6af8
GKH
374 pci_set_master(pcidev);
375
e9eff9d6 376 netdev = alloc_etherdev(sizeof(struct adapter));
4d6f6af8
GKH
377 if (!netdev) {
378 err = -ENOMEM;
379 goto err_out_exit_slic_probe;
380 }
4d6f6af8
GKH
381
382 SET_NETDEV_DEV(netdev, &pcidev->dev);
383
384 pci_set_drvdata(pcidev, netdev);
385 adapter = netdev_priv(netdev);
386 adapter->netdev = netdev;
387 adapter->pcidev = pcidev;
388
389 mmio_start = pci_resource_start(pcidev, 0);
390 mmio_len = pci_resource_len(pcidev, 0);
391
4d6f6af8 392
e8bc9b7a 393/* memmapped_ioaddr = (u32)ioremap_nocache(mmio_start, mmio_len);*/
4d6f6af8 394 memmapped_ioaddr = ioremap(mmio_start, mmio_len);
4d6f6af8
GKH
395 if (!memmapped_ioaddr) {
396 DBG_ERROR("%s cannot remap MMIO region %lx @ %lx\n",
397 __func__, mmio_len, mmio_start);
1025744a 398 goto err_out_free_netdev;
4d6f6af8
GKH
399 }
400
4d6f6af8
GKH
401 slic_config_pci(pcidev);
402
403 slic_init_driver();
404
405 slic_init_adapter(netdev,
406 pcidev, pci_tbl_entry, memmapped_ioaddr, cards_found);
407
408 status = slic_card_locate(adapter);
409 if (status) {
410 DBG_ERROR("%s cannot locate card\n", __func__);
411 goto err_out_free_mmio_region;
412 }
413
414 card = adapter->card;
415
416 if (!adapter->allocated) {
417 card->adapters_allocated++;
418 adapter->allocated = 1;
419 }
420
4d6f6af8
GKH
421 status = slic_card_init(card, adapter);
422
423 if (status != STATUS_SUCCESS) {
424 card->state = CARD_FAIL;
425 adapter->state = ADAPT_FAIL;
426 adapter->linkstate = LINK_DOWN;
427 DBG_ERROR("slic_card_init FAILED status[%x]\n", status);
428 } else {
429 slic_adapter_set_hwaddr(adapter);
430 }
431
432 netdev->base_addr = (unsigned long)adapter->memorybase;
433 netdev->irq = adapter->irq;
434 netdev->open = slic_entry_open;
435 netdev->stop = slic_entry_halt;
436 netdev->hard_start_xmit = slic_xmit_start;
437 netdev->do_ioctl = slic_ioctl;
438 netdev->set_mac_address = slic_mac_set_address;
4d6f6af8 439 netdev->get_stats = slic_get_stats;
4d6f6af8
GKH
440 netdev->set_multicast_list = slic_mcast_set_list;
441
442 slic_debug_adapter_create(adapter);
443
444 strcpy(netdev->name, "eth%d");
445 err = register_netdev(netdev);
446 if (err) {
447 DBG_ERROR("Cannot register net device, aborting.\n");
448 goto err_out_unmap;
449 }
450
4d6f6af8 451 cards_found++;
4d6f6af8
GKH
452
453 return status;
454
455err_out_unmap:
456 iounmap(memmapped_ioaddr);
4d6f6af8
GKH
457err_out_free_mmio_region:
458 release_mem_region(mmio_start, mmio_len);
1025744a
LD
459err_out_free_netdev:
460 free_netdev(netdev);
4d6f6af8 461err_out_exit_slic_probe:
f25fda72 462 pci_release_regions(pcidev);
4d6f6af8
GKH
463 DBG_ERROR("%s EXIT jiffies[%lx] cpu %d\n", __func__, jiffies,
464 smp_processor_id());
1025744a
LD
465err_out_disable_pci:
466 pci_disable_device(pcidev);
467 return err;
4d6f6af8
GKH
468}
469
e9eff9d6 470static int slic_entry_open(struct net_device *dev)
4d6f6af8 471{
e9eff9d6
LD
472 struct adapter *adapter = (struct adapter *) netdev_priv(dev);
473 struct sliccard *card = adapter->card;
474 u32 locked = 0;
4d6f6af8
GKH
475 int status;
476
477 ASSERT(adapter);
478 ASSERT(card);
4d6f6af8
GKH
479
480 netif_stop_queue(adapter->netdev);
481
e9eff9d6
LD
482 spin_lock_irqsave(&slic_global.driver_lock.lock,
483 slic_global.driver_lock.flags);
4d6f6af8
GKH
484 locked = 1;
485 if (!adapter->activated) {
486 card->adapters_activated++;
487 slic_global.num_slic_ports_active++;
488 adapter->activated = 1;
489 }
490 status = slic_if_init(adapter);
491
492 if (status != STATUS_SUCCESS) {
493 if (adapter->activated) {
494 card->adapters_activated--;
495 slic_global.num_slic_ports_active--;
496 adapter->activated = 0;
497 }
498 if (locked) {
e9eff9d6
LD
499 spin_unlock_irqrestore(&slic_global.driver_lock.lock,
500 slic_global.driver_lock.flags);
4d6f6af8
GKH
501 locked = 0;
502 }
503 return status;
504 }
4d6f6af8
GKH
505 if (!card->master)
506 card->master = adapter;
4d6f6af8
GKH
507
508 if (locked) {
e9eff9d6
LD
509 spin_unlock_irqrestore(&slic_global.driver_lock.lock,
510 slic_global.driver_lock.flags);
4d6f6af8
GKH
511 locked = 0;
512 }
4d6f6af8
GKH
513
514 return STATUS_SUCCESS;
515}
516
e9eff9d6 517static void __devexit slic_entry_remove(struct pci_dev *pcidev)
4d6f6af8
GKH
518{
519 struct net_device *dev = pci_get_drvdata(pcidev);
e9eff9d6 520 u32 mmio_start = 0;
4d6f6af8 521 uint mmio_len = 0;
e9eff9d6
LD
522 struct adapter *adapter = (struct adapter *) netdev_priv(dev);
523 struct sliccard *card;
786ed801 524 struct mcast_address *mcaddr, *mlist;
4d6f6af8
GKH
525
526 ASSERT(adapter);
4d6f6af8
GKH
527 slic_adapter_freeresources(adapter);
528 slic_unmap_mmio_space(adapter);
4d6f6af8
GKH
529 unregister_netdev(dev);
530
531 mmio_start = pci_resource_start(pcidev, 0);
532 mmio_len = pci_resource_len(pcidev, 0);
533
4d6f6af8
GKH
534 release_mem_region(mmio_start, mmio_len);
535
4d6f6af8 536 iounmap((void __iomem *)dev->base_addr);
786ed801
LD
537 /* free multicast addresses */
538 mlist = adapter->mcastaddrs;
539 while (mlist) {
540 mcaddr = mlist;
541 mlist = mlist->next;
542 kfree(mcaddr);
543 }
4d6f6af8
GKH
544 ASSERT(adapter->card);
545 card = adapter->card;
546 ASSERT(card->adapters_allocated);
547 card->adapters_allocated--;
548 adapter->allocated = 0;
4d6f6af8 549 if (!card->adapters_allocated) {
e9eff9d6 550 struct sliccard *curr_card = slic_global.slic_card;
4d6f6af8
GKH
551 if (curr_card == card) {
552 slic_global.slic_card = card->next;
553 } else {
554 while (curr_card->next != card)
555 curr_card = curr_card->next;
556 ASSERT(curr_card);
557 curr_card->next = card->next;
558 }
559 ASSERT(slic_global.num_slic_cards);
560 slic_global.num_slic_cards--;
561 slic_card_cleanup(card);
562 }
e9eff9d6 563 kfree(dev);
f25fda72 564 pci_release_regions(pcidev);
4d6f6af8
GKH
565}
566
e9eff9d6 567static int slic_entry_halt(struct net_device *dev)
4d6f6af8 568{
e9eff9d6
LD
569 struct adapter *adapter = (struct adapter *)netdev_priv(dev);
570 struct sliccard *card = adapter->card;
571 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
4d6f6af8 572
e9eff9d6
LD
573 spin_lock_irqsave(&slic_global.driver_lock.lock,
574 slic_global.driver_lock.flags);
4d6f6af8 575 ASSERT(card);
77faefa3 576 netif_stop_queue(adapter->netdev);
4d6f6af8
GKH
577 adapter->state = ADAPT_DOWN;
578 adapter->linkstate = LINK_DOWN;
579 adapter->upr_list = NULL;
580 adapter->upr_busy = 0;
581 adapter->devflags_prev = 0;
4d6f6af8 582 ASSERT(card->adapter[adapter->cardindex] == adapter);
62f691a3 583 slic_reg32_write(&slic_regs->slic_icr, ICR_INT_OFF, FLUSH);
4d6f6af8
GKH
584 adapter->all_reg_writes++;
585 adapter->icr_reg_writes++;
586 slic_config_clear(adapter);
4d6f6af8
GKH
587 if (adapter->activated) {
588 card->adapters_activated--;
589 slic_global.num_slic_ports_active--;
590 adapter->activated = 0;
591 }
592#ifdef AUTOMATIC_RESET
62f691a3 593 slic_reg32_write(&slic_regs->slic_reset_iface, 0, FLUSH);
4d6f6af8
GKH
594#endif
595 /*
e8bc9b7a 596 * Reset the adapter's cmd queues
4d6f6af8
GKH
597 */
598 slic_cmdq_reset(adapter);
4d6f6af8
GKH
599
600#ifdef AUTOMATIC_RESET
e8bc9b7a 601 if (!card->adapters_activated)
4d6f6af8 602 slic_card_init(card, adapter);
4d6f6af8
GKH
603#endif
604
e9eff9d6
LD
605 spin_unlock_irqrestore(&slic_global.driver_lock.lock,
606 slic_global.driver_lock.flags);
4d6f6af8
GKH
607 return STATUS_SUCCESS;
608}
609
e9eff9d6 610static int slic_ioctl(struct net_device *dev, struct ifreq *rq, int cmd)
4d6f6af8
GKH
611{
612 ASSERT(rq);
4d6f6af8
GKH
613 switch (cmd) {
614 case SIOCSLICSETINTAGG:
615 {
e9eff9d6
LD
616 struct adapter *adapter = (struct adapter *)
617 netdev_priv(dev);
618 u32 data[7];
619 u32 intagg;
4d6f6af8
GKH
620
621 if (copy_from_user(data, rq->ifr_data, 28)) {
622 DBG_ERROR
623 ("copy_from_user FAILED getting initial \
624 params\n");
625 return -EFAULT;
626 }
627 intagg = data[0];
628 printk(KERN_EMERG
629 "%s: set interrupt aggregation to %d\n",
630 __func__, intagg);
631 slic_intagg_set(adapter, intagg);
632 return 0;
633 }
4d6f6af8
GKH
634
635#ifdef SLIC_TRACE_DUMP_ENABLED
636 case SIOCSLICTRACEDUMP:
637 {
638 ulong data[7];
639 ulong value;
640
641 DBG_IOCTL("slic_ioctl SIOCSLIC_TRACE_DUMP\n");
642
643 if (copy_from_user(data, rq->ifr_data, 28)) {
644 PRINT_ERROR
645 ("slic: copy_from_user FAILED getting \
646 initial simba param\n");
647 return -EFAULT;
648 }
649
650 value = data[0];
651 if (tracemon_request == SLIC_DUMP_DONE) {
652 PRINT_ERROR
653 ("ATK Diagnostic Trace Dump Requested\n");
654 tracemon_request = SLIC_DUMP_REQUESTED;
655 tracemon_request_type = value;
656 tracemon_timestamp = jiffies;
657 } else if ((tracemon_request == SLIC_DUMP_REQUESTED) ||
658 (tracemon_request ==
659 SLIC_DUMP_IN_PROGRESS)) {
660 PRINT_ERROR
661 ("ATK Diagnostic Trace Dump Requested but \
662 already in progress... ignore\n");
663 } else {
664 PRINT_ERROR
665 ("ATK Diagnostic Trace Dump Requested\n");
666 tracemon_request = SLIC_DUMP_REQUESTED;
667 tracemon_request_type = value;
668 tracemon_timestamp = jiffies;
669 }
670 return 0;
671 }
672#endif
673#if SLIC_ETHTOOL_SUPPORT
674 case SIOCETHTOOL:
675 {
e9eff9d6
LD
676 struct adapter *adapter = (struct adapter *)
677 netdev_priv(dev);
4d6f6af8
GKH
678 struct ethtool_cmd data;
679 struct ethtool_cmd ecmd;
680
681 ASSERT(adapter);
4d6f6af8
GKH
682 if (copy_from_user(&ecmd, rq->ifr_data, sizeof(ecmd)))
683 return -EFAULT;
684
685 if (ecmd.cmd == ETHTOOL_GSET) {
686 data.supported =
687 (SUPPORTED_10baseT_Half |
688 SUPPORTED_10baseT_Full |
689 SUPPORTED_100baseT_Half |
690 SUPPORTED_100baseT_Full |
691 SUPPORTED_Autoneg | SUPPORTED_MII);
692 data.port = PORT_MII;
693 data.transceiver = XCVR_INTERNAL;
694 data.phy_address = 0;
695 if (adapter->linkspeed == LINK_100MB)
696 data.speed = SPEED_100;
697 else if (adapter->linkspeed == LINK_10MB)
698 data.speed = SPEED_10;
699 else
700 data.speed = 0;
701
702 if (adapter->linkduplex == LINK_FULLD)
703 data.duplex = DUPLEX_FULL;
704 else
705 data.duplex = DUPLEX_HALF;
706
707 data.autoneg = AUTONEG_ENABLE;
708 data.maxtxpkt = 1;
709 data.maxrxpkt = 1;
710 if (copy_to_user
711 (rq->ifr_data, &data, sizeof(data)))
712 return -EFAULT;
713
714 } else if (ecmd.cmd == ETHTOOL_SSET) {
715 if (!capable(CAP_NET_ADMIN))
716 return -EPERM;
717
718 if (adapter->linkspeed == LINK_100MB)
719 data.speed = SPEED_100;
720 else if (adapter->linkspeed == LINK_10MB)
721 data.speed = SPEED_10;
722 else
723 data.speed = 0;
724
725 if (adapter->linkduplex == LINK_FULLD)
726 data.duplex = DUPLEX_FULL;
727 else
728 data.duplex = DUPLEX_HALF;
729
730 data.autoneg = AUTONEG_ENABLE;
731 data.maxtxpkt = 1;
732 data.maxrxpkt = 1;
733 if ((ecmd.speed != data.speed) ||
734 (ecmd.duplex != data.duplex)) {
e9eff9d6
LD
735 u32 speed;
736 u32 duplex;
4d6f6af8
GKH
737
738 if (ecmd.speed == SPEED_10) {
739 speed = 0;
740 SLIC_DISPLAY
741 ("%s: slic ETHTOOL set \
742 link speed==10MB",
743 dev->name);
744 } else {
745 speed = PCR_SPEED_100;
746 SLIC_DISPLAY
747 ("%s: slic ETHTOOL set \
748 link speed==100MB",
749 dev->name);
750 }
751 if (ecmd.duplex == DUPLEX_FULL) {
752 duplex = PCR_DUPLEX_FULL;
753 SLIC_DISPLAY
754 (": duplex==FULL\n");
755 } else {
756 duplex = 0;
757 SLIC_DISPLAY
758 (": duplex==HALF\n");
759 }
760 slic_link_config(adapter,
761 speed, duplex);
762 slic_link_event_handler(adapter);
763 }
764 }
765 return 0;
766 }
767#endif
768 default:
4d6f6af8
GKH
769 return -EOPNOTSUPP;
770 }
771}
772
773#define XMIT_FAIL_LINK_STATE 1
774#define XMIT_FAIL_ZERO_LENGTH 2
775#define XMIT_FAIL_HOSTCMD_FAIL 3
776
e9eff9d6
LD
777static void slic_xmit_build_request(struct adapter *adapter,
778 struct slic_hostcmd *hcmd, struct sk_buff *skb)
4d6f6af8 779{
e9eff9d6 780 struct slic_host64_cmd *ihcmd;
4d6f6af8
GKH
781 ulong phys_addr;
782
783 ihcmd = &hcmd->cmd64;
784
785 ihcmd->flags = (adapter->port << IHFLG_IFSHFT);
786 ihcmd->command = IHCMD_XMT_REQ;
787 ihcmd->u.slic_buffers.totlen = skb->len;
e9eff9d6
LD
788 phys_addr = pci_map_single(adapter->pcidev, skb->data, skb->len,
789 PCI_DMA_TODEVICE);
4d6f6af8
GKH
790 ihcmd->u.slic_buffers.bufs[0].paddrl = SLIC_GET_ADDR_LOW(phys_addr);
791 ihcmd->u.slic_buffers.bufs[0].paddrh = SLIC_GET_ADDR_HIGH(phys_addr);
792 ihcmd->u.slic_buffers.bufs[0].length = skb->len;
793#if defined(CONFIG_X86_64)
e9eff9d6
LD
794 hcmd->cmdsize = (u32) ((((u64)&ihcmd->u.slic_buffers.bufs[1] -
795 (u64) hcmd) + 31) >> 5);
4d6f6af8 796#elif defined(CONFIG_X86)
e9eff9d6
LD
797 hcmd->cmdsize = ((((u32) &ihcmd->u.slic_buffers.bufs[1] -
798 (u32) hcmd) + 31) >> 5);
4d6f6af8
GKH
799#else
800 Stop Compilation;
801#endif
802}
803
804#define NORMAL_ETHFRAME 0
805
e9eff9d6 806static int slic_xmit_start(struct sk_buff *skb, struct net_device *dev)
4d6f6af8 807{
e9eff9d6
LD
808 struct sliccard *card;
809 struct adapter *adapter = (struct adapter *)netdev_priv(dev);
810 struct slic_hostcmd *hcmd = NULL;
811 u32 status = 0;
812 u32 skbtype = NORMAL_ETHFRAME;
813 void *offloadcmd = NULL;
4d6f6af8
GKH
814
815 card = adapter->card;
816 ASSERT(card);
817/*
818 DBG_ERROR("xmit_start (%s) ENTER skb[%p] len[%d] linkstate[%x] state[%x]\n",
819 adapter->netdev->name, skb, skb->len, adapter->linkstate,
820 adapter->state);
821*/
822 if ((adapter->linkstate != LINK_UP) ||
823 (adapter->state != ADAPT_UP) || (card->state != CARD_UP)) {
824 status = XMIT_FAIL_LINK_STATE;
825 goto xmit_fail;
826
827 } else if (skb->len == 0) {
828 status = XMIT_FAIL_ZERO_LENGTH;
829 goto xmit_fail;
830 }
831
832 if (skbtype == NORMAL_ETHFRAME) {
833 hcmd = slic_cmdq_getfree(adapter);
834 if (!hcmd) {
835 adapter->xmitq_full = 1;
836 status = XMIT_FAIL_HOSTCMD_FAIL;
837 goto xmit_fail;
838 }
839 ASSERT(hcmd->pslic_handle);
840 ASSERT(hcmd->cmd64.hosthandle ==
841 hcmd->pslic_handle->token.handle_token);
842 hcmd->skb = skb;
843 hcmd->busy = 1;
844 hcmd->type = SLIC_CMD_DUMB;
845 if (skbtype == NORMAL_ETHFRAME)
846 slic_xmit_build_request(adapter, hcmd, skb);
847 }
848 adapter->stats.tx_packets++;
849 adapter->stats.tx_bytes += skb->len;
850
851#ifdef DEBUG_DUMP
852 if (adapter->kill_card) {
68cf95f3 853 struct slic_host64_cmd ihcmd;
4d6f6af8
GKH
854
855 ihcmd = &hcmd->cmd64;
856
857 ihcmd->flags |= 0x40;
858 adapter->kill_card = 0; /* only do this once */
859 }
860#endif
861 if (hcmd->paddrh == 0) {
62f691a3
GKH
862 slic_reg32_write(&adapter->slic_regs->slic_cbar,
863 (hcmd->paddrl | hcmd->cmdsize), DONT_FLUSH);
4d6f6af8 864 } else {
28980a3c
GKH
865 slic_reg64_write(adapter, &adapter->slic_regs->slic_cbar64,
866 (hcmd->paddrl | hcmd->cmdsize),
867 &adapter->slic_regs->slic_addr_upper,
868 hcmd->paddrh, DONT_FLUSH);
4d6f6af8
GKH
869 }
870xmit_done:
871 return 0;
872xmit_fail:
873 slic_xmit_fail(adapter, skb, offloadcmd, skbtype, status);
874 goto xmit_done;
875}
876
e9eff9d6 877static void slic_xmit_fail(struct adapter *adapter,
4d6f6af8 878 struct sk_buff *skb,
e9eff9d6 879 void *cmd, u32 skbtype, u32 status)
4d6f6af8
GKH
880{
881 if (adapter->xmitq_full)
77faefa3 882 netif_stop_queue(adapter->netdev);
4d6f6af8
GKH
883 if ((cmd == NULL) && (status <= XMIT_FAIL_HOSTCMD_FAIL)) {
884 switch (status) {
885 case XMIT_FAIL_LINK_STATE:
886 DBG_ERROR
887 ("(%s) reject xmit skb[%p: %x] linkstate[%s] \
888 adapter[%s:%d] card[%s:%d]\n",
889 adapter->netdev->name, skb, skb->pkt_type,
890 SLIC_LINKSTATE(adapter->linkstate),
891 SLIC_ADAPTER_STATE(adapter->state), adapter->state,
892 SLIC_CARD_STATE(adapter->card->state),
893 adapter->card->state);
894 break;
895 case XMIT_FAIL_ZERO_LENGTH:
896 DBG_ERROR
897 ("xmit_start skb->len == 0 skb[%p] type[%x]!!!! \n",
898 skb, skb->pkt_type);
899 break;
900 case XMIT_FAIL_HOSTCMD_FAIL:
901 DBG_ERROR
902 ("xmit_start skb[%p] type[%x] No host commands \
903 available !!!! \n",
904 skb, skb->pkt_type);
905 break;
906 default:
907 ASSERT(0);
908 }
909 }
910 dev_kfree_skb(skb);
911 adapter->stats.tx_dropped++;
912}
913
e9eff9d6
LD
914static void slic_rcv_handle_error(struct adapter *adapter,
915 struct slic_rcvbuf *rcvbuf)
4d6f6af8 916{
e9eff9d6 917 struct slic_hddr_wds *hdr = (struct slic_hddr_wds *)rcvbuf->data;
4d6f6af8
GKH
918
919 if (adapter->devid != SLIC_1GB_DEVICE_ID) {
920 if (hdr->frame_status14 & VRHSTAT_802OE)
921 adapter->if_events.oflow802++;
922 if (hdr->frame_status14 & VRHSTAT_TPOFLO)
923 adapter->if_events.Tprtoflow++;
924 if (hdr->frame_status_b14 & VRHSTATB_802UE)
925 adapter->if_events.uflow802++;
926 if (hdr->frame_status_b14 & VRHSTATB_RCVE) {
927 adapter->if_events.rcvearly++;
928 adapter->stats.rx_fifo_errors++;
929 }
930 if (hdr->frame_status_b14 & VRHSTATB_BUFF) {
931 adapter->if_events.Bufov++;
932 adapter->stats.rx_over_errors++;
933 }
934 if (hdr->frame_status_b14 & VRHSTATB_CARRE) {
935 adapter->if_events.Carre++;
936 adapter->stats.tx_carrier_errors++;
937 }
938 if (hdr->frame_status_b14 & VRHSTATB_LONGE)
939 adapter->if_events.Longe++;
940 if (hdr->frame_status_b14 & VRHSTATB_PREA)
941 adapter->if_events.Invp++;
942 if (hdr->frame_status_b14 & VRHSTATB_CRC) {
943 adapter->if_events.Crc++;
944 adapter->stats.rx_crc_errors++;
945 }
946 if (hdr->frame_status_b14 & VRHSTATB_DRBL)
947 adapter->if_events.Drbl++;
948 if (hdr->frame_status_b14 & VRHSTATB_CODE)
949 adapter->if_events.Code++;
950 if (hdr->frame_status_b14 & VRHSTATB_TPCSUM)
951 adapter->if_events.TpCsum++;
952 if (hdr->frame_status_b14 & VRHSTATB_TPHLEN)
953 adapter->if_events.TpHlen++;
954 if (hdr->frame_status_b14 & VRHSTATB_IPCSUM)
955 adapter->if_events.IpCsum++;
956 if (hdr->frame_status_b14 & VRHSTATB_IPLERR)
957 adapter->if_events.IpLen++;
958 if (hdr->frame_status_b14 & VRHSTATB_IPHERR)
959 adapter->if_events.IpHlen++;
960 } else {
961 if (hdr->frame_statusGB & VGBSTAT_XPERR) {
e9eff9d6 962 u32 xerr = hdr->frame_statusGB >> VGBSTAT_XERRSHFT;
4d6f6af8
GKH
963
964 if (xerr == VGBSTAT_XCSERR)
965 adapter->if_events.TpCsum++;
966 if (xerr == VGBSTAT_XUFLOW)
967 adapter->if_events.Tprtoflow++;
968 if (xerr == VGBSTAT_XHLEN)
969 adapter->if_events.TpHlen++;
970 }
971 if (hdr->frame_statusGB & VGBSTAT_NETERR) {
e9eff9d6 972 u32 nerr =
4d6f6af8
GKH
973 (hdr->
974 frame_statusGB >> VGBSTAT_NERRSHFT) &
975 VGBSTAT_NERRMSK;
976 if (nerr == VGBSTAT_NCSERR)
977 adapter->if_events.IpCsum++;
978 if (nerr == VGBSTAT_NUFLOW)
979 adapter->if_events.IpLen++;
980 if (nerr == VGBSTAT_NHLEN)
981 adapter->if_events.IpHlen++;
982 }
983 if (hdr->frame_statusGB & VGBSTAT_LNKERR) {
e9eff9d6 984 u32 lerr = hdr->frame_statusGB & VGBSTAT_LERRMSK;
4d6f6af8
GKH
985
986 if (lerr == VGBSTAT_LDEARLY)
987 adapter->if_events.rcvearly++;
988 if (lerr == VGBSTAT_LBOFLO)
989 adapter->if_events.Bufov++;
990 if (lerr == VGBSTAT_LCODERR)
991 adapter->if_events.Code++;
992 if (lerr == VGBSTAT_LDBLNBL)
993 adapter->if_events.Drbl++;
994 if (lerr == VGBSTAT_LCRCERR)
995 adapter->if_events.Crc++;
996 if (lerr == VGBSTAT_LOFLO)
997 adapter->if_events.oflow802++;
998 if (lerr == VGBSTAT_LUFLO)
999 adapter->if_events.uflow802++;
1000 }
1001 }
1002 return;
1003}
1004
1005#define TCP_OFFLOAD_FRAME_PUSHFLAG 0x10000000
1006#define M_FAST_PATH 0x0040
1007
e9eff9d6 1008static void slic_rcv_handler(struct adapter *adapter)
4d6f6af8
GKH
1009{
1010 struct sk_buff *skb;
e9eff9d6
LD
1011 struct slic_rcvbuf *rcvbuf;
1012 u32 frames = 0;
4d6f6af8
GKH
1013
1014 while ((skb = slic_rcvqueue_getnext(adapter))) {
e9eff9d6 1015 u32 rx_bytes;
4d6f6af8
GKH
1016
1017 ASSERT(skb->head);
e9eff9d6 1018 rcvbuf = (struct slic_rcvbuf *)skb->head;
4d6f6af8
GKH
1019 adapter->card->events++;
1020 if (rcvbuf->status & IRHDDR_ERR) {
1021 adapter->rx_errors++;
1022 slic_rcv_handle_error(adapter, rcvbuf);
1023 slic_rcvqueue_reinsert(adapter, skb);
1024 continue;
1025 }
1026
e9eff9d6
LD
1027 if (!slic_mac_filter(adapter, (struct ether_header *)
1028 rcvbuf->data)) {
4d6f6af8
GKH
1029 slic_rcvqueue_reinsert(adapter, skb);
1030 continue;
1031 }
1032 skb_pull(skb, SLIC_RCVBUF_HEADSIZE);
1033 rx_bytes = (rcvbuf->length & IRHDDR_FLEN_MSK);
1034 skb_put(skb, rx_bytes);
1035 adapter->stats.rx_packets++;
1036 adapter->stats.rx_bytes += rx_bytes;
1037#if SLIC_OFFLOAD_IP_CHECKSUM
1038 skb->ip_summed = CHECKSUM_UNNECESSARY;
1039#endif
1040
1041 skb->dev = adapter->netdev;
1042 skb->protocol = eth_type_trans(skb, skb->dev);
1043 netif_rx(skb);
1044
1045 ++frames;
1046#if SLIC_INTERRUPT_PROCESS_LIMIT
1047 if (frames >= SLIC_RCVQ_MAX_PROCESS_ISR) {
1048 adapter->rcv_interrupt_yields++;
1049 break;
1050 }
1051#endif
1052 }
1053 adapter->max_isr_rcvs = max(adapter->max_isr_rcvs, frames);
1054}
1055
e9eff9d6 1056static void slic_xmit_complete(struct adapter *adapter)
4d6f6af8 1057{
e9eff9d6
LD
1058 struct slic_hostcmd *hcmd;
1059 struct slic_rspbuf *rspbuf;
1060 u32 frames = 0;
1061 struct slic_handle_word slic_handle_word;
4d6f6af8
GKH
1062
1063 do {
1064 rspbuf = slic_rspqueue_getnext(adapter);
1065 if (!rspbuf)
1066 break;
1067 adapter->xmit_completes++;
1068 adapter->card->events++;
1069 /*
1070 Get the complete host command buffer
1071 */
1072 slic_handle_word.handle_token = rspbuf->hosthandle;
1073 ASSERT(slic_handle_word.handle_index);
1074 ASSERT(slic_handle_word.handle_index <= SLIC_CMDQ_MAXCMDS);
1075 hcmd =
e9eff9d6
LD
1076 (struct slic_hostcmd *)
1077 adapter->slic_handles[slic_handle_word.handle_index].
1078 address;
1079/* hcmd = (struct slic_hostcmd *) rspbuf->hosthandle; */
4d6f6af8
GKH
1080 ASSERT(hcmd);
1081 ASSERT(hcmd->pslic_handle ==
1082 &adapter->slic_handles[slic_handle_word.handle_index]);
1083/*
1084 DBG_ERROR("xmit_complete (%s) hcmd[%p] hosthandle[%x]\n",
1085 adapter->netdev->name, hcmd, hcmd->cmd64.hosthandle);
1086 DBG_ERROR(" skb[%p] len %d hcmdtype[%x]\n", hcmd->skb,
1087 hcmd->skb->len, hcmd->type);
1088*/
1089 if (hcmd->type == SLIC_CMD_DUMB) {
1090 if (hcmd->skb)
1091 dev_kfree_skb_irq(hcmd->skb);
1092 slic_cmdq_putdone_irq(adapter, hcmd);
1093 }
1094 rspbuf->status = 0;
1095 rspbuf->hosthandle = 0;
1096 frames++;
1097 } while (1);
1098 adapter->max_isr_xmits = max(adapter->max_isr_xmits, frames);
1099}
1100
1101static irqreturn_t slic_interrupt(int irq, void *dev_id)
1102{
e9eff9d6
LD
1103 struct net_device *dev = (struct net_device *)dev_id;
1104 struct adapter *adapter = (struct adapter *)netdev_priv(dev);
1105 u32 isr;
4d6f6af8
GKH
1106
1107 if ((adapter->pshmem) && (adapter->pshmem->isr)) {
62f691a3
GKH
1108 slic_reg32_write(&adapter->slic_regs->slic_icr,
1109 ICR_INT_MASK, FLUSH);
4d6f6af8
GKH
1110 isr = adapter->isrcopy = adapter->pshmem->isr;
1111 adapter->pshmem->isr = 0;
1112 adapter->num_isrs++;
1113 switch (adapter->card->state) {
1114 case CARD_UP:
1115 if (isr & ~ISR_IO) {
1116 if (isr & ISR_ERR) {
1117 adapter->error_interrupts++;
1118 if (isr & ISR_RMISS) {
1119 int count;
1120 int pre_count;
1121 int errors;
1122
e9eff9d6 1123 struct slic_rcvqueue *rcvq =
4d6f6af8
GKH
1124 &adapter->rcvqueue;
1125
1126 adapter->
1127 error_rmiss_interrupts++;
1128 if (!rcvq->errors)
1129 rcv_count = rcvq->count;
1130 pre_count = rcvq->count;
1131 errors = rcvq->errors;
1132
1133 while (rcvq->count <
1134 SLIC_RCVQ_FILLTHRESH) {
1135 count =
1136 slic_rcvqueue_fill
1137 (adapter);
1138 if (!count)
1139 break;
1140 }
4d6f6af8
GKH
1141 } else if (isr & ISR_XDROP) {
1142 DBG_ERROR
1143 ("isr & ISR_ERR [%x] \
1144 ISR_XDROP \n",
1145 isr);
1146 } else {
1147 DBG_ERROR
1148 ("isr & ISR_ERR [%x]\n",
1149 isr);
1150 }
1151 }
1152
1153 if (isr & ISR_LEVENT) {
4d6f6af8
GKH
1154 adapter->linkevent_interrupts++;
1155 slic_link_event_handler(adapter);
1156 }
1157
1158 if ((isr & ISR_UPC) ||
1159 (isr & ISR_UPCERR) || (isr & ISR_UPCBSY)) {
1160 adapter->upr_interrupts++;
1161 slic_upr_request_complete(adapter, isr);
1162 }
1163 }
1164
1165 if (isr & ISR_RCV) {
1166 adapter->rcv_interrupts++;
1167 slic_rcv_handler(adapter);
1168 }
1169
1170 if (isr & ISR_CMD) {
1171 adapter->xmit_interrupts++;
1172 slic_xmit_complete(adapter);
1173 }
1174 break;
1175
1176 case CARD_DOWN:
1177 if ((isr & ISR_UPC) ||
1178 (isr & ISR_UPCERR) || (isr & ISR_UPCBSY)) {
1179 adapter->upr_interrupts++;
1180 slic_upr_request_complete(adapter, isr);
1181 }
1182 break;
1183
1184 default:
1185 break;
1186 }
1187
1188 adapter->isrcopy = 0;
1189 adapter->all_reg_writes += 2;
1190 adapter->isr_reg_writes++;
62f691a3 1191 slic_reg32_write(&adapter->slic_regs->slic_isr, 0, FLUSH);
4d6f6af8
GKH
1192 } else {
1193 adapter->false_interrupts++;
1194 }
1195 return IRQ_HANDLED;
1196}
1197
1198/*
1199 * slic_link_event_handler -
1200 *
1201 * Initiate a link configuration sequence. The link configuration begins
1202 * by issuing a READ_LINK_STATUS command to the Utility Processor on the
1203 * SLIC. Since the command finishes asynchronously, the slic_upr_comlete
1204 * routine will follow it up witha UP configuration write command, which
1205 * will also complete asynchronously.
1206 *
1207 */
e9eff9d6 1208static void slic_link_event_handler(struct adapter *adapter)
4d6f6af8
GKH
1209{
1210 int status;
e9eff9d6 1211 struct slic_shmem *pshmem;
4d6f6af8
GKH
1212
1213 if (adapter->state != ADAPT_UP) {
1214 /* Adapter is not operational. Ignore. */
1215 return;
1216 }
1217
e9eff9d6 1218 pshmem = (struct slic_shmem *)adapter->phys_shmem;
4d6f6af8
GKH
1219
1220#if defined(CONFIG_X86_64)
4d6f6af8
GKH
1221 status = slic_upr_request(adapter,
1222 SLIC_UPR_RLSR,
1223 SLIC_GET_ADDR_LOW(&pshmem->linkstatus),
1224 SLIC_GET_ADDR_HIGH(&pshmem->linkstatus),
1225 0, 0);
1226#elif defined(CONFIG_X86)
1227 status = slic_upr_request(adapter, SLIC_UPR_RLSR,
e9eff9d6 1228 (u32) &pshmem->linkstatus, /* no 4GB wrap guaranteed */
4d6f6af8
GKH
1229 0, 0, 0);
1230#else
1231 Stop compilation;
1232#endif
1233 ASSERT((status == STATUS_SUCCESS) || (status == STATUS_PENDING));
1234}
1235
e9eff9d6 1236static void slic_init_cleanup(struct adapter *adapter)
4d6f6af8 1237{
4d6f6af8 1238 if (adapter->intrregistered) {
4d6f6af8
GKH
1239 adapter->intrregistered = 0;
1240 free_irq(adapter->netdev->irq, adapter->netdev);
1241
1242 }
1243 if (adapter->pshmem) {
4d6f6af8 1244 pci_free_consistent(adapter->pcidev,
66615321 1245 sizeof(struct slic_shmem),
4d6f6af8
GKH
1246 adapter->pshmem, adapter->phys_shmem);
1247 adapter->pshmem = NULL;
1248 adapter->phys_shmem = (dma_addr_t) NULL;
1249 }
a0a1cbef 1250
4d6f6af8 1251 if (adapter->pingtimerset) {
4d6f6af8
GKH
1252 adapter->pingtimerset = 0;
1253 del_timer(&adapter->pingtimer);
1254 }
a0a1cbef 1255
4d6f6af8
GKH
1256 slic_rspqueue_free(adapter);
1257 slic_cmdq_free(adapter);
1258 slic_rcvqueue_free(adapter);
4d6f6af8
GKH
1259}
1260
e9eff9d6 1261static struct net_device_stats *slic_get_stats(struct net_device *dev)
4d6f6af8 1262{
e9eff9d6 1263 struct adapter *adapter = (struct adapter *)netdev_priv(dev);
4d6f6af8
GKH
1264 struct net_device_stats *stats;
1265
1266 ASSERT(adapter);
1267 stats = &adapter->stats;
1268 stats->collisions = adapter->slic_stats.iface.xmit_collisions;
1269 stats->rx_errors = adapter->slic_stats.iface.rcv_errors;
1270 stats->tx_errors = adapter->slic_stats.iface.xmt_errors;
1271 stats->rx_missed_errors = adapter->slic_stats.iface.rcv_discards;
1272 stats->tx_heartbeat_errors = 0;
1273 stats->tx_aborted_errors = 0;
1274 stats->tx_window_errors = 0;
1275 stats->tx_fifo_errors = 0;
1276 stats->rx_frame_errors = 0;
1277 stats->rx_length_errors = 0;
1278 return &adapter->stats;
1279}
4d6f6af8
GKH
1280
1281/*
1282 * Allocate a mcast_address structure to hold the multicast address.
1283 * Link it in.
1284 */
e9eff9d6 1285static int slic_mcast_add_list(struct adapter *adapter, char *address)
4d6f6af8 1286{
e9eff9d6
LD
1287 struct mcast_address *mcaddr, *mlist;
1288 bool equaladdr;
4d6f6af8
GKH
1289
1290 /* Check to see if it already exists */
1291 mlist = adapter->mcastaddrs;
1292 while (mlist) {
1293 ETHER_EQ_ADDR(mlist->address, address, equaladdr);
1294 if (equaladdr)
1295 return STATUS_SUCCESS;
1296 mlist = mlist->next;
1297 }
1298
1299 /* Doesn't already exist. Allocate a structure to hold it */
2bb34736 1300 mcaddr = kmalloc(sizeof(struct mcast_address), GFP_KERNEL);
4d6f6af8
GKH
1301 if (mcaddr == NULL)
1302 return 1;
1303
1304 memcpy(mcaddr->address, address, 6);
1305
1306 mcaddr->next = adapter->mcastaddrs;
1307 adapter->mcastaddrs = mcaddr;
1308
1309 return STATUS_SUCCESS;
1310}
1311
1312/*
1313 * Functions to obtain the CRC corresponding to the destination mac address.
1314 * This is a standard ethernet CRC in that it is a 32-bit, reflected CRC using
1315 * the polynomial:
1316 * x^32 + x^26 + x^23 + x^22 + x^16 + x^12 + x^11 + x^10 + x^8 + x^7 + x^5 +
1317 * x^4 + x^2 + x^1.
1318 *
1319 * After the CRC for the 6 bytes is generated (but before the value is
1320 * complemented),
1321 * we must then transpose the value and return bits 30-23.
1322 *
1323 */
1324static u32 slic_crc_table[256]; /* Table of CRCs for all possible byte values */
1325static u32 slic_crc_init; /* Is table initialized */
1326
1327/*
1328 * Contruct the CRC32 table
1329 */
e9eff9d6 1330static void slic_mcast_init_crc32(void)
4d6f6af8 1331{
e9eff9d6
LD
1332 u32 c; /* CRC shit reg */
1333 u32 e = 0; /* Poly X-or pattern */
4d6f6af8
GKH
1334 int i; /* counter */
1335 int k; /* byte being shifted into crc */
1336
1337 static int p[] = { 0, 1, 2, 4, 5, 7, 8, 10, 11, 12, 16, 22, 23, 26 };
1338
1339 for (i = 0; i < sizeof(p) / sizeof(int); i++)
1340 e |= 1L << (31 - p[i]);
1341
1342 for (i = 1; i < 256; i++) {
1343 c = i;
1344 for (k = 8; k; k--)
1345 c = c & 1 ? (c >> 1) ^ e : c >> 1;
1346 slic_crc_table[i] = c;
1347 }
1348}
1349
1350/*
1351 * Return the MAC hast as described above.
1352 */
e9eff9d6 1353static unsigned char slic_mcast_get_mac_hash(char *macaddr)
4d6f6af8 1354{
e9eff9d6
LD
1355 u32 crc;
1356 char *p;
4d6f6af8 1357 int i;
e9eff9d6 1358 unsigned char machash = 0;
4d6f6af8
GKH
1359
1360 if (!slic_crc_init) {
1361 slic_mcast_init_crc32();
1362 slic_crc_init = 1;
1363 }
1364
1365 crc = 0xFFFFFFFF; /* Preload shift register, per crc-32 spec */
1366 for (i = 0, p = macaddr; i < 6; ++p, ++i)
1367 crc = (crc >> 8) ^ slic_crc_table[(crc ^ *p) & 0xFF];
1368
1369 /* Return bits 1-8, transposed */
1370 for (i = 1; i < 9; i++)
1371 machash |= (((crc >> i) & 1) << (8 - i));
1372
1373 return machash;
1374}
1375
e9eff9d6 1376static void slic_mcast_set_bit(struct adapter *adapter, char *address)
4d6f6af8 1377{
e9eff9d6 1378 unsigned char crcpoly;
4d6f6af8
GKH
1379
1380 /* Get the CRC polynomial for the mac address */
1381 crcpoly = slic_mcast_get_mac_hash(address);
1382
1383 /* We only have space on the SLIC for 64 entries. Lop
1384 * off the top two bits. (2^6 = 64)
1385 */
1386 crcpoly &= 0x3F;
1387
1388 /* OR in the new bit into our 64 bit mask. */
e9eff9d6 1389 adapter->mcastmask |= (u64) 1 << crcpoly;
4d6f6af8
GKH
1390}
1391
e9eff9d6 1392static void slic_mcast_set_list(struct net_device *dev)
4d6f6af8 1393{
e9eff9d6 1394 struct adapter *adapter = (struct adapter *)netdev_priv(dev);
4d6f6af8
GKH
1395 int status = STATUS_SUCCESS;
1396 int i;
e9eff9d6 1397 char *addresses;
4d6f6af8
GKH
1398 struct dev_mc_list *mc_list = dev->mc_list;
1399 int mc_count = dev->mc_count;
1400
1401 ASSERT(adapter);
1402
1403 for (i = 1; i <= mc_count; i++) {
e9eff9d6 1404 addresses = (char *) &mc_list->dmi_addr;
4d6f6af8
GKH
1405 if (mc_list->dmi_addrlen == 6) {
1406 status = slic_mcast_add_list(adapter, addresses);
1407 if (status != STATUS_SUCCESS)
1408 break;
1409 } else {
1410 status = -EINVAL;
1411 break;
1412 }
1413 slic_mcast_set_bit(adapter, addresses);
1414 mc_list = mc_list->next;
1415 }
1416
4d6f6af8
GKH
1417 if (adapter->devflags_prev != dev->flags) {
1418 adapter->macopts = MAC_DIRECTED;
1419 if (dev->flags) {
1420 if (dev->flags & IFF_BROADCAST)
1421 adapter->macopts |= MAC_BCAST;
1422 if (dev->flags & IFF_PROMISC)
1423 adapter->macopts |= MAC_PROMISC;
1424 if (dev->flags & IFF_ALLMULTI)
1425 adapter->macopts |= MAC_ALLMCAST;
1426 if (dev->flags & IFF_MULTICAST)
1427 adapter->macopts |= MAC_MCAST;
1428 }
1429 adapter->devflags_prev = dev->flags;
b574488e 1430 slic_config_set(adapter, true);
4d6f6af8
GKH
1431 } else {
1432 if (status == STATUS_SUCCESS)
1433 slic_mcast_set_mask(adapter);
1434 }
1435 return;
1436}
1437
e9eff9d6 1438static void slic_mcast_set_mask(struct adapter *adapter)
4d6f6af8 1439{
e9eff9d6 1440 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
4d6f6af8 1441
4d6f6af8
GKH
1442 if (adapter->macopts & (MAC_ALLMCAST | MAC_PROMISC)) {
1443 /* Turn on all multicast addresses. We have to do this for
1444 * promiscuous mode as well as ALLMCAST mode. It saves the
1445 * Microcode from having to keep state about the MAC
1446 * configuration.
1447 */
62f691a3
GKH
1448 slic_reg32_write(&slic_regs->slic_mcastlow, 0xFFFFFFFF, FLUSH);
1449 slic_reg32_write(&slic_regs->slic_mcasthigh, 0xFFFFFFFF,
1450 FLUSH);
4d6f6af8
GKH
1451 } else {
1452 /* Commit our multicast mast to the SLIC by writing to the
1453 * multicast address mask registers
1454 */
62f691a3
GKH
1455 slic_reg32_write(&slic_regs->slic_mcastlow,
1456 (u32)(adapter->mcastmask & 0xFFFFFFFF), FLUSH);
1457 slic_reg32_write(&slic_regs->slic_mcasthigh,
1458 (u32)((adapter->mcastmask >> 32) & 0xFFFFFFFF), FLUSH);
4d6f6af8
GKH
1459 }
1460}
1461
e9eff9d6 1462static void slic_timer_ping(ulong dev)
4d6f6af8 1463{
e9eff9d6
LD
1464 struct adapter *adapter;
1465 struct sliccard *card;
4d6f6af8
GKH
1466
1467 ASSERT(dev);
4bcd4267 1468 adapter = netdev_priv((struct net_device *)dev);
4d6f6af8
GKH
1469 ASSERT(adapter);
1470 card = adapter->card;
1471 ASSERT(card);
4d6f6af8 1472
db7a673a 1473 adapter->pingtimer.expires = jiffies + (PING_TIMER_INTERVAL * HZ);
4d6f6af8
GKH
1474 add_timer(&adapter->pingtimer);
1475}
1476
4d6f6af8
GKH
1477/*
1478 * slic_if_init
1479 *
1480 * Perform initialization of our slic interface.
1481 *
1482 */
e9eff9d6 1483static int slic_if_init(struct adapter *adapter)
4d6f6af8 1484{
e9eff9d6 1485 struct sliccard *card = adapter->card;
4d6f6af8 1486 struct net_device *dev = adapter->netdev;
e9eff9d6
LD
1487 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
1488 struct slic_shmem *pshmem;
4d6f6af8
GKH
1489 int status = 0;
1490
1491 ASSERT(card);
4d6f6af8
GKH
1492
1493 /* adapter should be down at this point */
1494 if (adapter->state != ADAPT_DOWN) {
1495 DBG_ERROR("slic_if_init adapter->state != ADAPT_DOWN\n");
1496 return -EIO;
1497 }
1498 ASSERT(adapter->linkstate == LINK_DOWN);
1499
1500 adapter->devflags_prev = dev->flags;
1501 adapter->macopts = MAC_DIRECTED;
1502 if (dev->flags) {
e8bc9b7a 1503 if (dev->flags & IFF_BROADCAST)
4d6f6af8 1504 adapter->macopts |= MAC_BCAST;
e8bc9b7a 1505 if (dev->flags & IFF_PROMISC)
4d6f6af8 1506 adapter->macopts |= MAC_PROMISC;
e8bc9b7a 1507 if (dev->flags & IFF_ALLMULTI)
4d6f6af8 1508 adapter->macopts |= MAC_ALLMCAST;
e8bc9b7a 1509 if (dev->flags & IFF_MULTICAST)
4d6f6af8 1510 adapter->macopts |= MAC_MCAST;
4d6f6af8
GKH
1511 }
1512 status = slic_adapter_allocresources(adapter);
1513 if (status != STATUS_SUCCESS) {
1514 DBG_ERROR
1515 ("slic_if_init: slic_adapter_allocresources FAILED %x\n",
1516 status);
1517 slic_adapter_freeresources(adapter);
1518 return status;
1519 }
1520
1521 if (!adapter->queues_initialized) {
4d6f6af8
GKH
1522 if (slic_rspqueue_init(adapter))
1523 return -ENOMEM;
4d6f6af8
GKH
1524 if (slic_cmdq_init(adapter))
1525 return -ENOMEM;
4d6f6af8
GKH
1526 if (slic_rcvqueue_init(adapter))
1527 return -ENOMEM;
1528 adapter->queues_initialized = 1;
1529 }
4d6f6af8 1530
62f691a3 1531 slic_reg32_write(&slic_regs->slic_icr, ICR_INT_OFF, FLUSH);
e9eff9d6 1532 mdelay(1);
4d6f6af8
GKH
1533
1534 if (!adapter->isp_initialized) {
e9eff9d6 1535 pshmem = (struct slic_shmem *)adapter->phys_shmem;
4d6f6af8 1536
e9eff9d6
LD
1537 spin_lock_irqsave(&adapter->bit64reglock.lock,
1538 adapter->bit64reglock.flags);
4d6f6af8
GKH
1539
1540#if defined(CONFIG_X86_64)
62f691a3
GKH
1541 slic_reg32_write(&slic_regs->slic_addr_upper,
1542 SLIC_GET_ADDR_HIGH(&pshmem->isr), DONT_FLUSH);
1543 slic_reg32_write(&slic_regs->slic_isp,
1544 SLIC_GET_ADDR_LOW(&pshmem->isr), FLUSH);
4d6f6af8 1545#elif defined(CONFIG_X86)
62f691a3
GKH
1546 slic_reg32_write(&slic_regs->slic_addr_upper, 0, DONT_FLUSH);
1547 slic_reg32_write(&slic_regs->slic_isp, (u32)&pshmem->isr, FLUSH);
4d6f6af8
GKH
1548#else
1549 Stop Compilations
1550#endif
e9eff9d6
LD
1551 spin_unlock_irqrestore(&adapter->bit64reglock.lock,
1552 adapter->bit64reglock.flags);
4d6f6af8
GKH
1553 adapter->isp_initialized = 1;
1554 }
1555
1556 adapter->state = ADAPT_UP;
1557 if (!card->loadtimerset) {
1558 init_timer(&card->loadtimer);
1559 card->loadtimer.expires =
db7a673a 1560 jiffies + (SLIC_LOADTIMER_PERIOD * HZ);
4d6f6af8
GKH
1561 card->loadtimer.data = (ulong) card;
1562 card->loadtimer.function = &slic_timer_load_check;
1563 add_timer(&card->loadtimer);
1564
1565 card->loadtimerset = 1;
1566 }
a0a1cbef 1567
4d6f6af8 1568 if (!adapter->pingtimerset) {
4d6f6af8
GKH
1569 init_timer(&adapter->pingtimer);
1570 adapter->pingtimer.expires =
db7a673a 1571 jiffies + (PING_TIMER_INTERVAL * HZ);
4d6f6af8
GKH
1572 adapter->pingtimer.data = (ulong) dev;
1573 adapter->pingtimer.function = &slic_timer_ping;
1574 add_timer(&adapter->pingtimer);
1575 adapter->pingtimerset = 1;
1576 adapter->card->pingstatus = ISR_PINGMASK;
1577 }
4d6f6af8
GKH
1578
1579 /*
1580 * clear any pending events, then enable interrupts
1581 */
4d6f6af8
GKH
1582 adapter->isrcopy = 0;
1583 adapter->pshmem->isr = 0;
62f691a3
GKH
1584 slic_reg32_write(&slic_regs->slic_isr, 0, FLUSH);
1585 slic_reg32_write(&slic_regs->slic_icr, ICR_INT_ON, FLUSH);
4d6f6af8 1586
4d6f6af8
GKH
1587 slic_link_config(adapter, LINK_AUTOSPEED, LINK_AUTOD);
1588 slic_link_event_handler(adapter);
1589
4d6f6af8
GKH
1590 return STATUS_SUCCESS;
1591}
1592
e9eff9d6 1593static void slic_unmap_mmio_space(struct adapter *adapter)
4d6f6af8 1594{
4d6f6af8
GKH
1595 if (adapter->slic_regs)
1596 iounmap(adapter->slic_regs);
1597 adapter->slic_regs = NULL;
4d6f6af8
GKH
1598}
1599
e9eff9d6 1600static int slic_adapter_allocresources(struct adapter *adapter)
4d6f6af8
GKH
1601{
1602 if (!adapter->intrregistered) {
1603 int retval;
1604
e9eff9d6
LD
1605 spin_unlock_irqrestore(&slic_global.driver_lock.lock,
1606 slic_global.driver_lock.flags);
4d6f6af8
GKH
1607
1608 retval = request_irq(adapter->netdev->irq,
1609 &slic_interrupt,
1610 IRQF_SHARED,
1611 adapter->netdev->name, adapter->netdev);
1612
e9eff9d6
LD
1613 spin_lock_irqsave(&slic_global.driver_lock.lock,
1614 slic_global.driver_lock.flags);
4d6f6af8
GKH
1615
1616 if (retval) {
1617 DBG_ERROR("slicoss: request_irq (%s) FAILED [%x]\n",
1618 adapter->netdev->name, retval);
1619 return retval;
1620 }
1621 adapter->intrregistered = 1;
4d6f6af8
GKH
1622 }
1623 return STATUS_SUCCESS;
1624}
1625
e9eff9d6 1626static void slic_config_pci(struct pci_dev *pcidev)
4d6f6af8
GKH
1627{
1628 u16 pci_command;
1629 u16 new_command;
1630
1631 pci_read_config_word(pcidev, PCI_COMMAND, &pci_command);
4d6f6af8
GKH
1632
1633 new_command = pci_command | PCI_COMMAND_MASTER
1634 | PCI_COMMAND_MEMORY
1635 | PCI_COMMAND_INVALIDATE
1636 | PCI_COMMAND_PARITY | PCI_COMMAND_SERR | PCI_COMMAND_FAST_BACK;
e8bc9b7a 1637 if (pci_command != new_command)
4d6f6af8 1638 pci_write_config_word(pcidev, PCI_COMMAND, new_command);
4d6f6af8
GKH
1639}
1640
e9eff9d6 1641static void slic_adapter_freeresources(struct adapter *adapter)
4d6f6af8 1642{
4d6f6af8 1643 slic_init_cleanup(adapter);
e9eff9d6 1644 memset(&adapter->stats, 0, sizeof(struct net_device_stats));
4d6f6af8
GKH
1645 adapter->error_interrupts = 0;
1646 adapter->rcv_interrupts = 0;
1647 adapter->xmit_interrupts = 0;
1648 adapter->linkevent_interrupts = 0;
1649 adapter->upr_interrupts = 0;
1650 adapter->num_isrs = 0;
1651 adapter->xmit_completes = 0;
1652 adapter->rcv_broadcasts = 0;
1653 adapter->rcv_multicasts = 0;
1654 adapter->rcv_unicasts = 0;
4d6f6af8
GKH
1655}
1656
1657/*
1658 * slic_link_config
1659 *
1660 * Write phy control to configure link duplex/speed
1661 *
1662 */
e9eff9d6
LD
1663static void slic_link_config(struct adapter *adapter,
1664 u32 linkspeed, u32 linkduplex)
4d6f6af8 1665{
62f691a3 1666 u32 __iomem *wphy;
e9eff9d6
LD
1667 u32 speed;
1668 u32 duplex;
1669 u32 phy_config;
1670 u32 phy_advreg;
1671 u32 phy_gctlreg;
4d6f6af8 1672
e8bc9b7a 1673 if (adapter->state != ADAPT_UP)
4d6f6af8 1674 return;
4d6f6af8
GKH
1675
1676 ASSERT((adapter->devid == SLIC_1GB_DEVICE_ID)
1677 || (adapter->devid == SLIC_2GB_DEVICE_ID));
1678
1679 if (linkspeed > LINK_1000MB)
1680 linkspeed = LINK_AUTOSPEED;
1681 if (linkduplex > LINK_AUTOD)
1682 linkduplex = LINK_AUTOD;
1683
62f691a3
GKH
1684 wphy = &adapter->slic_regs->slic_wphy;
1685
4d6f6af8
GKH
1686 if ((linkspeed == LINK_AUTOSPEED) || (linkspeed == LINK_1000MB)) {
1687 if (adapter->flags & ADAPT_FLAGS_FIBERMEDIA) {
1688 /* We've got a fiber gigabit interface, and register
1689 * 4 is different in fiber mode than in copper mode
1690 */
1691
1692 /* advertise FD only @1000 Mb */
1693 phy_advreg = (MIICR_REG_4 | (PAR_ADV1000XFD));
1694 /* enable PAUSE frames */
1695 phy_advreg |= PAR_ASYMPAUSE_FIBER;
62f691a3 1696 slic_reg32_write(wphy, phy_advreg, FLUSH);
4d6f6af8
GKH
1697
1698 if (linkspeed == LINK_AUTOSPEED) {
1699 /* reset phy, enable auto-neg */
1700 phy_config =
1701 (MIICR_REG_PCR |
1702 (PCR_RESET | PCR_AUTONEG |
1703 PCR_AUTONEG_RST));
62f691a3 1704 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1705 } else { /* forced 1000 Mb FD*/
1706 /* power down phy to break link
1707 this may not work) */
1708 phy_config = (MIICR_REG_PCR | PCR_POWERDOWN);
62f691a3 1709 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1710 /* wait, Marvell says 1 sec,
1711 try to get away with 10 ms */
e9eff9d6 1712 mdelay(10);
4d6f6af8
GKH
1713
1714 /* disable auto-neg, set speed/duplex,
1715 soft reset phy, powerup */
1716 phy_config =
1717 (MIICR_REG_PCR |
1718 (PCR_RESET | PCR_SPEED_1000 |
1719 PCR_DUPLEX_FULL));
62f691a3 1720 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1721 }
1722 } else { /* copper gigabit */
1723
1724 /* Auto-Negotiate or 1000 Mb must be auto negotiated
1725 * We've got a copper gigabit interface, and
1726 * register 4 is different in copper mode than
1727 * in fiber mode
1728 */
1729 if (linkspeed == LINK_AUTOSPEED) {
1730 /* advertise 10/100 Mb modes */
1731 phy_advreg =
1732 (MIICR_REG_4 |
1733 (PAR_ADV100FD | PAR_ADV100HD | PAR_ADV10FD
1734 | PAR_ADV10HD));
1735 } else {
1736 /* linkspeed == LINK_1000MB -
1737 don't advertise 10/100 Mb modes */
1738 phy_advreg = MIICR_REG_4;
1739 }
1740 /* enable PAUSE frames */
1741 phy_advreg |= PAR_ASYMPAUSE;
1742 /* required by the Cicada PHY */
1743 phy_advreg |= PAR_802_3;
62f691a3 1744 slic_reg32_write(wphy, phy_advreg, FLUSH);
4d6f6af8
GKH
1745 /* advertise FD only @1000 Mb */
1746 phy_gctlreg = (MIICR_REG_9 | (PGC_ADV1000FD));
62f691a3 1747 slic_reg32_write(wphy, phy_gctlreg, FLUSH);
4d6f6af8
GKH
1748
1749 if (adapter->subsysid != SLIC_1GB_CICADA_SUBSYS_ID) {
1750 /* if a Marvell PHY
1751 enable auto crossover */
1752 phy_config =
1753 (MIICR_REG_16 | (MRV_REG16_XOVERON));
62f691a3 1754 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1755
1756 /* reset phy, enable auto-neg */
1757 phy_config =
1758 (MIICR_REG_PCR |
1759 (PCR_RESET | PCR_AUTONEG |
1760 PCR_AUTONEG_RST));
62f691a3 1761 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1762 } else { /* it's a Cicada PHY */
1763 /* enable and restart auto-neg (don't reset) */
1764 phy_config =
1765 (MIICR_REG_PCR |
1766 (PCR_AUTONEG | PCR_AUTONEG_RST));
62f691a3 1767 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1768 }
1769 }
1770 } else {
1771 /* Forced 10/100 */
1772 if (linkspeed == LINK_10MB)
1773 speed = 0;
1774 else
1775 speed = PCR_SPEED_100;
1776 if (linkduplex == LINK_HALFD)
1777 duplex = 0;
1778 else
1779 duplex = PCR_DUPLEX_FULL;
1780
1781 if (adapter->subsysid != SLIC_1GB_CICADA_SUBSYS_ID) {
1782 /* if a Marvell PHY
1783 disable auto crossover */
1784 phy_config = (MIICR_REG_16 | (MRV_REG16_XOVEROFF));
62f691a3 1785 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1786 }
1787
1788 /* power down phy to break link (this may not work) */
1789 phy_config = (MIICR_REG_PCR | (PCR_POWERDOWN | speed | duplex));
62f691a3 1790 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1791
1792 /* wait, Marvell says 1 sec, try to get away with 10 ms */
e9eff9d6 1793 mdelay(10);
4d6f6af8
GKH
1794
1795 if (adapter->subsysid != SLIC_1GB_CICADA_SUBSYS_ID) {
1796 /* if a Marvell PHY
1797 disable auto-neg, set speed,
1798 soft reset phy, powerup */
1799 phy_config =
1800 (MIICR_REG_PCR | (PCR_RESET | speed | duplex));
62f691a3 1801 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1802 } else { /* it's a Cicada PHY */
1803 /* disable auto-neg, set speed, powerup */
1804 phy_config = (MIICR_REG_PCR | (speed | duplex));
62f691a3 1805 slic_reg32_write(wphy, phy_config, FLUSH);
4d6f6af8
GKH
1806 }
1807 }
4d6f6af8
GKH
1808}
1809
e9eff9d6 1810static void slic_card_cleanup(struct sliccard *card)
4d6f6af8 1811{
4d6f6af8
GKH
1812 if (card->loadtimerset) {
1813 card->loadtimerset = 0;
1814 del_timer(&card->loadtimer);
1815 }
1816
1817 slic_debug_card_destroy(card);
1818
e9eff9d6 1819 kfree(card);
4d6f6af8
GKH
1820}
1821
e9eff9d6 1822static int slic_card_download_gbrcv(struct adapter *adapter)
4d6f6af8 1823{
470c5736
LD
1824 const struct firmware *fw;
1825 const char *file = "";
1826 int ret;
e9eff9d6
LD
1827 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
1828 u32 codeaddr;
874073ea
LD
1829 u32 instruction;
1830 int index = 0;
e9eff9d6 1831 u32 rcvucodelen = 0;
4d6f6af8
GKH
1832
1833 switch (adapter->devid) {
1834 case SLIC_2GB_DEVICE_ID:
a390c479 1835 file = "slicoss/oasisrcvucode.sys";
4d6f6af8
GKH
1836 break;
1837 case SLIC_1GB_DEVICE_ID:
a390c479 1838 file = "slicoss/gbrcvucode.sys";
470c5736
LD
1839 break;
1840 default:
1841 ASSERT(0);
1842 break;
1843 }
1844
1845 ret = request_firmware(&fw, file, &adapter->pcidev->dev);
1846 if (ret) {
1847 printk(KERN_ERR "SLICOSS: Failed to load firmware %s\n", file);
1848 return ret;
1849 }
1850
874073ea
LD
1851 rcvucodelen = *(u32 *)(fw->data + index);
1852 index += 4;
470c5736
LD
1853 switch (adapter->devid) {
1854 case SLIC_2GB_DEVICE_ID:
1855 if (rcvucodelen != OasisRcvUCodeLen)
1856 return -EINVAL;
1857 break;
1858 case SLIC_1GB_DEVICE_ID:
1859 if (rcvucodelen != GBRcvUCodeLen)
1860 return -EINVAL;
4d6f6af8
GKH
1861 break;
1862 default:
1863 ASSERT(0);
1864 break;
1865 }
4d6f6af8 1866 /* start download */
62f691a3 1867 slic_reg32_write(&slic_regs->slic_rcv_wcs, SLIC_RCVWCS_BEGIN, FLUSH);
4d6f6af8
GKH
1868 /* download the rcv sequencer ucode */
1869 for (codeaddr = 0; codeaddr < rcvucodelen; codeaddr++) {
1870 /* write out instruction address */
62f691a3 1871 slic_reg32_write(&slic_regs->slic_rcv_wcs, codeaddr, FLUSH);
4d6f6af8 1872
874073ea
LD
1873 instruction = *(u32 *)(fw->data + index);
1874 index += 4;
4d6f6af8 1875 /* write out the instruction data low addr */
62f691a3 1876 slic_reg32_write(&slic_regs->slic_rcv_wcs, instruction, FLUSH);
4d6f6af8 1877
874073ea
LD
1878 instruction = *(u8 *)(fw->data + index);
1879 index++;
4d6f6af8 1880 /* write out the instruction data high addr */
62f691a3
GKH
1881 slic_reg32_write(&slic_regs->slic_rcv_wcs, (u8)instruction,
1882 FLUSH);
4d6f6af8
GKH
1883 }
1884
1885 /* download finished */
470c5736 1886 release_firmware(fw);
62f691a3 1887 slic_reg32_write(&slic_regs->slic_rcv_wcs, SLIC_RCVWCS_FINISH, FLUSH);
4d6f6af8
GKH
1888 return 0;
1889}
1890
e9eff9d6 1891static int slic_card_download(struct adapter *adapter)
4d6f6af8 1892{
470c5736
LD
1893 const struct firmware *fw;
1894 const char *file = "";
1895 int ret;
e9eff9d6 1896 u32 section;
4d6f6af8
GKH
1897 int thissectionsize;
1898 int codeaddr;
e9eff9d6 1899 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
874073ea 1900 u32 instruction;
e9eff9d6
LD
1901 u32 baseaddress;
1902 u32 failure;
1903 u32 i;
1904 u32 numsects = 0;
1905 u32 sectsize[3];
1906 u32 sectstart[3];
874073ea 1907 int ucode_start, index = 0;
4d6f6af8 1908
4d6f6af8
GKH
1909 switch (adapter->devid) {
1910 case SLIC_2GB_DEVICE_ID:
a390c479 1911 file = "slicoss/oasisdownload.sys";
4d6f6af8
GKH
1912 break;
1913 case SLIC_1GB_DEVICE_ID:
a390c479 1914 file = "slicoss/gbdownload.sys";
4d6f6af8
GKH
1915 break;
1916 default:
1917 ASSERT(0);
1918 break;
1919 }
470c5736
LD
1920 ret = request_firmware(&fw, file, &adapter->pcidev->dev);
1921 if (ret) {
1922 printk(KERN_ERR "SLICOSS: Failed to load firmware %s\n", file);
1923 return ret;
1924 }
874073ea
LD
1925 numsects = *(u32 *)(fw->data + index);
1926 index += 4;
4d6f6af8 1927 ASSERT(numsects <= 3);
874073ea
LD
1928 for (i = 0; i < numsects; i++) {
1929 sectsize[i] = *(u32 *)(fw->data + index);
1930 index += 4;
1931 }
1932 for (i = 0; i < numsects; i++) {
1933 sectstart[i] = *(u32 *)(fw->data + index);
1934 index += 4;
1935 }
1936 ucode_start = index;
1937 instruction = *(u32 *)(fw->data + index);
1938 index += 4;
4d6f6af8 1939 for (section = 0; section < numsects; section++) {
4d6f6af8
GKH
1940 baseaddress = sectstart[section];
1941 thissectionsize = sectsize[section] >> 3;
1942
1943 for (codeaddr = 0; codeaddr < thissectionsize; codeaddr++) {
4d6f6af8 1944 /* Write out instruction address */
62f691a3
GKH
1945 slic_reg32_write(&slic_regs->slic_wcs,
1946 baseaddress + codeaddr, FLUSH);
4d6f6af8 1947 /* Write out instruction to low addr */
62f691a3 1948 slic_reg32_write(&slic_regs->slic_wcs, instruction, FLUSH);
874073ea
LD
1949 instruction = *(u32 *)(fw->data + index);
1950 index += 4;
1951
4d6f6af8 1952 /* Write out instruction to high addr */
62f691a3 1953 slic_reg32_write(&slic_regs->slic_wcs, instruction, FLUSH);
874073ea
LD
1954 instruction = *(u32 *)(fw->data + index);
1955 index += 4;
4d6f6af8
GKH
1956 }
1957 }
874073ea 1958 index = ucode_start;
4d6f6af8 1959 for (section = 0; section < numsects; section++) {
874073ea 1960 instruction = *(u32 *)(fw->data + index);
4d6f6af8
GKH
1961 baseaddress = sectstart[section];
1962 if (baseaddress < 0x8000)
1963 continue;
1964 thissectionsize = sectsize[section] >> 3;
1965
4d6f6af8
GKH
1966 for (codeaddr = 0; codeaddr < thissectionsize; codeaddr++) {
1967 /* Write out instruction address */
62f691a3
GKH
1968 slic_reg32_write(&slic_regs->slic_wcs,
1969 SLIC_WCS_COMPARE | (baseaddress + codeaddr),
1970 FLUSH);
4d6f6af8 1971 /* Write out instruction to low addr */
62f691a3
GKH
1972 slic_reg32_write(&slic_regs->slic_wcs, instruction,
1973 FLUSH);
874073ea
LD
1974 instruction = *(u32 *)(fw->data + index);
1975 index += 4;
4d6f6af8 1976 /* Write out instruction to high addr */
62f691a3
GKH
1977 slic_reg32_write(&slic_regs->slic_wcs, instruction,
1978 FLUSH);
874073ea
LD
1979 instruction = *(u32 *)(fw->data + index);
1980 index += 4;
1981
4d6f6af8 1982 /* Check SRAM location zero. If it is non-zero. Abort.*/
874073ea 1983/* failure = readl((u32 __iomem *)&slic_regs->slic_reset);
4d6f6af8 1984 if (failure) {
470c5736 1985 release_firmware(fw);
4d6f6af8 1986 return -EIO;
874073ea 1987 }*/
4d6f6af8
GKH
1988 }
1989 }
470c5736 1990 release_firmware(fw);
4d6f6af8 1991 /* Everything OK, kick off the card */
e9eff9d6 1992 mdelay(10);
62f691a3 1993 slic_reg32_write(&slic_regs->slic_wcs, SLIC_WCS_START, FLUSH);
4d6f6af8
GKH
1994
1995 /* stall for 20 ms, long enough for ucode to init card
1996 and reach mainloop */
e9eff9d6 1997 mdelay(20);
4d6f6af8 1998
4d6f6af8
GKH
1999 return STATUS_SUCCESS;
2000}
2001
e9eff9d6 2002static void slic_adapter_set_hwaddr(struct adapter *adapter)
4d6f6af8 2003{
e9eff9d6 2004 struct sliccard *card = adapter->card;
4d6f6af8 2005
4d6f6af8
GKH
2006 if ((adapter->card) && (card->config_set)) {
2007 memcpy(adapter->macaddr,
2008 card->config.MacInfo[adapter->functionnumber].macaddrA,
e9eff9d6 2009 sizeof(struct slic_config_mac));
4d6f6af8
GKH
2010 if (!(adapter->currmacaddr[0] || adapter->currmacaddr[1] ||
2011 adapter->currmacaddr[2] || adapter->currmacaddr[3] ||
2012 adapter->currmacaddr[4] || adapter->currmacaddr[5])) {
2013 memcpy(adapter->currmacaddr, adapter->macaddr, 6);
2014 }
2015 if (adapter->netdev) {
2016 memcpy(adapter->netdev->dev_addr, adapter->currmacaddr,
2017 6);
2018 }
2019 }
4d6f6af8
GKH
2020}
2021
e9eff9d6 2022static void slic_intagg_set(struct adapter *adapter, u32 value)
4d6f6af8 2023{
62f691a3 2024 slic_reg32_write(&adapter->slic_regs->slic_intagg, value, FLUSH);
4d6f6af8
GKH
2025 adapter->card->loadlevel_current = value;
2026}
2027
e9eff9d6 2028static int slic_card_init(struct sliccard *card, struct adapter *adapter)
4d6f6af8 2029{
e9eff9d6
LD
2030 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
2031 struct slic_eeprom *peeprom;
2032 struct oslic_eeprom *pOeeprom;
4d6f6af8 2033 dma_addr_t phys_config;
e9eff9d6
LD
2034 u32 phys_configh;
2035 u32 phys_configl;
2036 u32 i = 0;
2037 struct slic_shmem *pshmem;
4d6f6af8
GKH
2038 int status;
2039 uint macaddrs = card->card_size;
2040 ushort eecodesize;
2041 ushort dramsize;
2042 ushort ee_chksum;
2043 ushort calc_chksum;
e9eff9d6
LD
2044 struct slic_config_mac *pmac;
2045 unsigned char fruformat;
2046 unsigned char oemfruformat;
2047 struct atk_fru *patkfru;
68cf95f3 2048 union oemfru *poemfru;
4d6f6af8 2049
4d6f6af8
GKH
2050 /* Reset everything except PCI configuration space */
2051 slic_soft_reset(adapter);
2052
2053 /* Download the microcode */
2054 status = slic_card_download(adapter);
2055
2056 if (status != STATUS_SUCCESS) {
2057 DBG_ERROR("SLIC download failed bus %d slot %d\n",
2058 (uint) adapter->busnumber,
2059 (uint) adapter->slotnumber);
2060 return status;
2061 }
2062
2063 if (!card->config_set) {
2064 peeprom = pci_alloc_consistent(adapter->pcidev,
e9eff9d6 2065 sizeof(struct slic_eeprom),
4d6f6af8
GKH
2066 &phys_config);
2067
2068 phys_configl = SLIC_GET_ADDR_LOW(phys_config);
2069 phys_configh = SLIC_GET_ADDR_HIGH(phys_config);
2070
4d6f6af8
GKH
2071 if (!peeprom) {
2072 DBG_ERROR
2073 ("SLIC eeprom read failed to get memory bus %d \
2074 slot %d\n",
2075 (uint) adapter->busnumber,
2076 (uint) adapter->slotnumber);
2077 return -ENOMEM;
2078 } else {
e9eff9d6 2079 memset(peeprom, 0, sizeof(struct slic_eeprom));
4d6f6af8 2080 }
62f691a3 2081 slic_reg32_write(&slic_regs->slic_icr, ICR_INT_OFF, FLUSH);
e9eff9d6
LD
2082 mdelay(1);
2083 pshmem = (struct slic_shmem *)adapter->phys_shmem;
4d6f6af8 2084
e9eff9d6
LD
2085 spin_lock_irqsave(&adapter->bit64reglock.lock,
2086 adapter->bit64reglock.flags);
62f691a3
GKH
2087 slic_reg32_write(&slic_regs->slic_addr_upper, 0, DONT_FLUSH);
2088 slic_reg32_write(&slic_regs->slic_isp,
2089 SLIC_GET_ADDR_LOW(&pshmem->isr), FLUSH);
e9eff9d6
LD
2090 spin_unlock_irqrestore(&adapter->bit64reglock.lock,
2091 adapter->bit64reglock.flags);
4d6f6af8
GKH
2092
2093 slic_config_get(adapter, phys_configl, phys_configh);
2094
2095 for (;;) {
2096 if (adapter->pshmem->isr) {
4d6f6af8
GKH
2097 if (adapter->pshmem->isr & ISR_UPC) {
2098 adapter->pshmem->isr = 0;
28980a3c
GKH
2099 slic_reg64_write(adapter,
2100 &slic_regs->slic_isp, 0,
2101 &slic_regs->slic_addr_upper,
2102 0, FLUSH);
62f691a3
GKH
2103 slic_reg32_write(&slic_regs->slic_isr,
2104 0, FLUSH);
4d6f6af8
GKH
2105
2106 slic_upr_request_complete(adapter, 0);
2107 break;
2108 } else {
2109 adapter->pshmem->isr = 0;
62f691a3
GKH
2110 slic_reg32_write(&slic_regs->slic_isr,
2111 0, FLUSH);
4d6f6af8
GKH
2112 }
2113 } else {
e9eff9d6 2114 mdelay(1);
4d6f6af8
GKH
2115 i++;
2116 if (i > 5000) {
2117 DBG_ERROR
874073ea
LD
2118 ("SLIC: %d config data fetch timed "
2119 "out!\n", adapter->port);
28980a3c
GKH
2120 slic_reg64_write(adapter,
2121 &slic_regs->slic_isp, 0,
2122 &slic_regs->slic_addr_upper,
2123 0, FLUSH);
4d6f6af8
GKH
2124 return -EINVAL;
2125 }
2126 }
2127 }
2128
2129 switch (adapter->devid) {
2130 /* Oasis card */
2131 case SLIC_2GB_DEVICE_ID:
2132 /* extract EEPROM data and pointers to EEPROM data */
e9eff9d6 2133 pOeeprom = (struct oslic_eeprom *) peeprom;
4d6f6af8
GKH
2134 eecodesize = pOeeprom->EecodeSize;
2135 dramsize = pOeeprom->DramSize;
2136 pmac = pOeeprom->MacInfo;
2137 fruformat = pOeeprom->FruFormat;
2138 patkfru = &pOeeprom->AtkFru;
2139 oemfruformat = pOeeprom->OemFruFormat;
2140 poemfru = &pOeeprom->OemFru;
2141 macaddrs = 2;
2142 /* Minor kludge for Oasis card
2143 get 2 MAC addresses from the
2144 EEPROM to ensure that function 1
2145 gets the Port 1 MAC address */
2146 break;
2147 default:
2148 /* extract EEPROM data and pointers to EEPROM data */
2149 eecodesize = peeprom->EecodeSize;
2150 dramsize = peeprom->DramSize;
2151 pmac = peeprom->u2.mac.MacInfo;
2152 fruformat = peeprom->FruFormat;
2153 patkfru = &peeprom->AtkFru;
2154 oemfruformat = peeprom->OemFruFormat;
2155 poemfru = &peeprom->OemFru;
2156 break;
2157 }
2158
b574488e 2159 card->config.EepromValid = false;
4d6f6af8
GKH
2160
2161 /* see if the EEPROM is valid by checking it's checksum */
2162 if ((eecodesize <= MAX_EECODE_SIZE) &&
2163 (eecodesize >= MIN_EECODE_SIZE)) {
2164
2165 ee_chksum =
e9eff9d6 2166 *(u16 *) ((char *) peeprom + (eecodesize - 2));
4d6f6af8
GKH
2167 /*
2168 calculate the EEPROM checksum
2169 */
2170 calc_chksum =
e9eff9d6 2171 ~slic_eeprom_cksum((char *) peeprom,
4d6f6af8
GKH
2172 (eecodesize - 2));
2173 /*
2174 if the ucdoe chksum flag bit worked,
2175 we wouldn't need this shit
2176 */
2177 if (ee_chksum == calc_chksum)
b574488e 2178 card->config.EepromValid = true;
4d6f6af8
GKH
2179 }
2180 /* copy in the DRAM size */
2181 card->config.DramSize = dramsize;
2182
2183 /* copy in the MAC address(es) */
2184 for (i = 0; i < macaddrs; i++) {
2185 memcpy(&card->config.MacInfo[i],
e9eff9d6 2186 &pmac[i], sizeof(struct slic_config_mac));
4d6f6af8 2187 }
4d6f6af8
GKH
2188
2189 /* copy the Alacritech FRU information */
2190 card->config.FruFormat = fruformat;
e9eff9d6
LD
2191 memcpy(&card->config.AtkFru, patkfru,
2192 sizeof(struct atk_fru));
4d6f6af8
GKH
2193
2194 pci_free_consistent(adapter->pcidev,
e9eff9d6 2195 sizeof(struct slic_eeprom),
4d6f6af8 2196 peeprom, phys_config);
4d6f6af8
GKH
2197
2198 if ((!card->config.EepromValid) &&
2199 (adapter->reg_params.fail_on_bad_eeprom)) {
28980a3c
GKH
2200 slic_reg64_write(adapter, &slic_regs->slic_isp, 0,
2201 &slic_regs->slic_addr_upper,
2202 0, FLUSH);
4d6f6af8
GKH
2203 DBG_ERROR
2204 ("unsupported CONFIGURATION EEPROM invalid\n");
2205 return -EINVAL;
2206 }
2207
2208 card->config_set = 1;
2209 }
2210
2211 if (slic_card_download_gbrcv(adapter)) {
2212 DBG_ERROR("%s unable to download GB receive microcode\n",
2213 __func__);
2214 return -EINVAL;
2215 }
2216
e8bc9b7a 2217 if (slic_global.dynamic_intagg)
4d6f6af8 2218 slic_intagg_set(adapter, 0);
e8bc9b7a 2219 else
4d6f6af8 2220 slic_intagg_set(adapter, intagg_delay);
4d6f6af8
GKH
2221
2222 /*
2223 * Initialize ping status to "ok"
2224 */
2225 card->pingstatus = ISR_PINGMASK;
2226
4d6f6af8
GKH
2227 /*
2228 * Lastly, mark our card state as up and return success
2229 */
2230 card->state = CARD_UP;
2231 card->reset_in_progress = 0;
4d6f6af8
GKH
2232
2233 return STATUS_SUCCESS;
2234}
2235
e9eff9d6 2236static u32 slic_card_locate(struct adapter *adapter)
4d6f6af8 2237{
e9eff9d6
LD
2238 struct sliccard *card = slic_global.slic_card;
2239 struct physcard *physcard = slic_global.phys_card;
4d6f6af8
GKH
2240 ushort card_hostid;
2241 u16 __iomem *hostid_reg;
2242 uint i;
2243 uint rdhostid_offset = 0;
2244
4d6f6af8
GKH
2245 switch (adapter->devid) {
2246 case SLIC_2GB_DEVICE_ID:
2247 rdhostid_offset = SLIC_RDHOSTID_2GB;
2248 break;
2249 case SLIC_1GB_DEVICE_ID:
2250 rdhostid_offset = SLIC_RDHOSTID_1GB;
2251 break;
2252 default:
2253 ASSERT(0);
2254 break;
2255 }
2256
2257 hostid_reg =
2258 (u16 __iomem *) (((u8 __iomem *) (adapter->slic_regs)) +
2259 rdhostid_offset);
4d6f6af8
GKH
2260
2261 /* read the 16 bit hostid from SRAM */
4d6f6af8 2262 card_hostid = (ushort) readw(hostid_reg);
4d6f6af8
GKH
2263
2264 /* Initialize a new card structure if need be */
2265 if (card_hostid == SLIC_HOSTID_DEFAULT) {
e9eff9d6 2266 card = kzalloc(sizeof(struct sliccard), GFP_KERNEL);
4d6f6af8
GKH
2267 if (card == NULL)
2268 return -ENOMEM;
2269
2270 card->next = slic_global.slic_card;
2271 slic_global.slic_card = card;
4d6f6af8
GKH
2272 card->busnumber = adapter->busnumber;
2273 card->slotnumber = adapter->slotnumber;
2274
2275 /* Find an available cardnum */
2276 for (i = 0; i < SLIC_MAX_CARDS; i++) {
2277 if (slic_global.cardnuminuse[i] == 0) {
2278 slic_global.cardnuminuse[i] = 1;
2279 card->cardnum = i;
2280 break;
2281 }
2282 }
2283 slic_global.num_slic_cards++;
4d6f6af8
GKH
2284
2285 slic_debug_card_create(card);
2286 } else {
4d6f6af8
GKH
2287 /* Card exists, find the card this adapter belongs to */
2288 while (card) {
4d6f6af8
GKH
2289 if (card->cardnum == card_hostid)
2290 break;
2291 card = card->next;
2292 }
2293 }
2294
2295 ASSERT(card);
2296 if (!card)
2297 return STATUS_FAILURE;
2298 /* Put the adapter in the card's adapter list */
2299 ASSERT(card->adapter[adapter->port] == NULL);
2300 if (!card->adapter[adapter->port]) {
2301 card->adapter[adapter->port] = adapter;
2302 adapter->card = card;
2303 }
2304
2305 card->card_size = 1; /* one port per *logical* card */
2306
2307 while (physcard) {
2308 for (i = 0; i < SLIC_MAX_PORTS; i++) {
2309 if (!physcard->adapter[i])
2310 continue;
2311 else
2312 break;
2313 }
2314 ASSERT(i != SLIC_MAX_PORTS);
2315 if (physcard->adapter[i]->slotnumber == adapter->slotnumber)
2316 break;
2317 physcard = physcard->next;
2318 }
2319 if (!physcard) {
2320 /* no structure allocated for this physical card yet */
2bb34736 2321 physcard = kzalloc(sizeof(struct physcard), GFP_KERNEL);
4d6f6af8 2322 ASSERT(physcard);
4d6f6af8 2323
4d6f6af8
GKH
2324 physcard->next = slic_global.phys_card;
2325 slic_global.phys_card = physcard;
2326 physcard->adapters_allocd = 1;
2327 } else {
2328 physcard->adapters_allocd++;
2329 }
2330 /* Note - this is ZERO relative */
2331 adapter->physport = physcard->adapters_allocd - 1;
2332
2333 ASSERT(physcard->adapter[adapter->physport] == NULL);
2334 physcard->adapter[adapter->physport] = adapter;
2335 adapter->physcard = physcard;
4d6f6af8
GKH
2336
2337 return 0;
2338}
2339
e9eff9d6 2340static void slic_soft_reset(struct adapter *adapter)
4d6f6af8
GKH
2341{
2342 if (adapter->card->state == CARD_UP) {
62f691a3 2343 slic_reg32_write(&adapter->slic_regs->slic_quiesce, 0, FLUSH);
e9eff9d6 2344 mdelay(1);
4d6f6af8 2345 }
4d6f6af8 2346
62f691a3
GKH
2347 slic_reg32_write(&adapter->slic_regs->slic_reset, SLIC_RESET_MAGIC,
2348 FLUSH);
e9eff9d6 2349 mdelay(1);
4d6f6af8
GKH
2350}
2351
e9eff9d6 2352static void slic_config_set(struct adapter *adapter, bool linkchange)
4d6f6af8 2353{
e9eff9d6
LD
2354 u32 value;
2355 u32 RcrReset;
2356 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
4d6f6af8 2357
4d6f6af8
GKH
2358 if (linkchange) {
2359 /* Setup MAC */
2360 slic_mac_config(adapter);
2361 RcrReset = GRCR_RESET;
2362 } else {
2363 slic_mac_address_config(adapter);
2364 RcrReset = 0;
2365 }
2366
2367 if (adapter->linkduplex == LINK_FULLD) {
2368 /* setup xmtcfg */
2369 value = (GXCR_RESET | /* Always reset */
2370 GXCR_XMTEN | /* Enable transmit */
2371 GXCR_PAUSEEN); /* Enable pause */
2372
62f691a3 2373 slic_reg32_write(&slic_regs->slic_wxcfg, value, FLUSH);
4d6f6af8
GKH
2374
2375 /* Setup rcvcfg last */
2376 value = (RcrReset | /* Reset, if linkchange */
2377 GRCR_CTLEN | /* Enable CTL frames */
2378 GRCR_ADDRAEN | /* Address A enable */
2379 GRCR_RCVBAD | /* Rcv bad frames */
2380 (GRCR_HASHSIZE << GRCR_HASHSIZE_SHIFT));
2381 } else {
2382 /* setup xmtcfg */
2383 value = (GXCR_RESET | /* Always reset */
2384 GXCR_XMTEN); /* Enable transmit */
2385
62f691a3 2386 slic_reg32_write(&slic_regs->slic_wxcfg, value, FLUSH);
4d6f6af8
GKH
2387
2388 /* Setup rcvcfg last */
2389 value = (RcrReset | /* Reset, if linkchange */
2390 GRCR_ADDRAEN | /* Address A enable */
2391 GRCR_RCVBAD | /* Rcv bad frames */
2392 (GRCR_HASHSIZE << GRCR_HASHSIZE_SHIFT));
2393 }
2394
2395 if (adapter->state != ADAPT_DOWN) {
2396 /* Only enable receive if we are restarting or running */
2397 value |= GRCR_RCVEN;
2398 }
2399
2400 if (adapter->macopts & MAC_PROMISC)
2401 value |= GRCR_RCVALL;
2402
62f691a3 2403 slic_reg32_write(&slic_regs->slic_wrcfg, value, FLUSH);
4d6f6af8
GKH
2404}
2405
2406/*
2407 * Turn off RCV and XMT, power down PHY
2408 */
e9eff9d6 2409static void slic_config_clear(struct adapter *adapter)
4d6f6af8 2410{
e9eff9d6
LD
2411 u32 value;
2412 u32 phy_config;
2413 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
4d6f6af8
GKH
2414
2415 /* Setup xmtcfg */
2416 value = (GXCR_RESET | /* Always reset */
2417 GXCR_PAUSEEN); /* Enable pause */
2418
62f691a3 2419 slic_reg32_write(&slic_regs->slic_wxcfg, value, FLUSH);
4d6f6af8
GKH
2420
2421 value = (GRCR_RESET | /* Always reset */
2422 GRCR_CTLEN | /* Enable CTL frames */
2423 GRCR_ADDRAEN | /* Address A enable */
2424 (GRCR_HASHSIZE << GRCR_HASHSIZE_SHIFT));
2425
62f691a3 2426 slic_reg32_write(&slic_regs->slic_wrcfg, value, FLUSH);
4d6f6af8
GKH
2427
2428 /* power down phy */
2429 phy_config = (MIICR_REG_PCR | (PCR_POWERDOWN));
62f691a3 2430 slic_reg32_write(&slic_regs->slic_wphy, phy_config, FLUSH);
4d6f6af8
GKH
2431}
2432
e9eff9d6
LD
2433static void slic_config_get(struct adapter *adapter, u32 config,
2434 u32 config_h)
4d6f6af8
GKH
2435{
2436 int status;
2437
2438 status = slic_upr_request(adapter,
2439 SLIC_UPR_RCONFIG,
e9eff9d6 2440 (u32) config, (u32) config_h, 0, 0);
4d6f6af8
GKH
2441 ASSERT(status == 0);
2442}
2443
e9eff9d6 2444static void slic_mac_address_config(struct adapter *adapter)
4d6f6af8 2445{
e9eff9d6
LD
2446 u32 value;
2447 u32 value2;
2448 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
4d6f6af8 2449
e9eff9d6 2450 value = *(u32 *) &adapter->currmacaddr[2];
4d6f6af8 2451 value = ntohl(value);
62f691a3
GKH
2452 slic_reg32_write(&slic_regs->slic_wraddral, value, FLUSH);
2453 slic_reg32_write(&slic_regs->slic_wraddrbl, value, FLUSH);
4d6f6af8 2454
e9eff9d6 2455 value2 = (u32) ((adapter->currmacaddr[0] << 8 |
4d6f6af8
GKH
2456 adapter->currmacaddr[1]) & 0xFFFF);
2457
62f691a3
GKH
2458 slic_reg32_write(&slic_regs->slic_wraddrah, value2, FLUSH);
2459 slic_reg32_write(&slic_regs->slic_wraddrbh, value2, FLUSH);
4d6f6af8 2460
4d6f6af8
GKH
2461 /* Write our multicast mask out to the card. This is done */
2462 /* here in addition to the slic_mcast_addr_set routine */
2463 /* because ALL_MCAST may have been enabled or disabled */
2464 slic_mcast_set_mask(adapter);
2465}
2466
e9eff9d6 2467static void slic_mac_config(struct adapter *adapter)
4d6f6af8 2468{
e9eff9d6
LD
2469 u32 value;
2470 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
4d6f6af8
GKH
2471
2472 /* Setup GMAC gaps */
2473 if (adapter->linkspeed == LINK_1000MB) {
2474 value = ((GMCR_GAPBB_1000 << GMCR_GAPBB_SHIFT) |
2475 (GMCR_GAPR1_1000 << GMCR_GAPR1_SHIFT) |
2476 (GMCR_GAPR2_1000 << GMCR_GAPR2_SHIFT));
2477 } else {
2478 value = ((GMCR_GAPBB_100 << GMCR_GAPBB_SHIFT) |
2479 (GMCR_GAPR1_100 << GMCR_GAPR1_SHIFT) |
2480 (GMCR_GAPR2_100 << GMCR_GAPR2_SHIFT));
2481 }
2482
2483 /* enable GMII */
2484 if (adapter->linkspeed == LINK_1000MB)
2485 value |= GMCR_GBIT;
2486
2487 /* enable fullduplex */
2488 if ((adapter->linkduplex == LINK_FULLD)
2489 || (adapter->macopts & MAC_LOOPBACK)) {
2490 value |= GMCR_FULLD;
2491 }
2492
2493 /* write mac config */
62f691a3 2494 slic_reg32_write(&slic_regs->slic_wmcfg, value, FLUSH);
4d6f6af8
GKH
2495
2496 /* setup mac addresses */
2497 slic_mac_address_config(adapter);
2498}
2499
e9eff9d6
LD
2500static bool slic_mac_filter(struct adapter *adapter,
2501 struct ether_header *ether_frame)
4d6f6af8 2502{
e9eff9d6
LD
2503 u32 opts = adapter->macopts;
2504 u32 *dhost4 = (u32 *)&ether_frame->ether_dhost[0];
2505 u16 *dhost2 = (u16 *)&ether_frame->ether_dhost[4];
2506 bool equaladdr;
4d6f6af8 2507
e8bc9b7a 2508 if (opts & MAC_PROMISC)
b574488e 2509 return true;
4d6f6af8
GKH
2510
2511 if ((*dhost4 == 0xFFFFFFFF) && (*dhost2 == 0xFFFF)) {
2512 if (opts & MAC_BCAST) {
2513 adapter->rcv_broadcasts++;
b574488e 2514 return true;
4d6f6af8 2515 } else {
b574488e 2516 return false;
4d6f6af8
GKH
2517 }
2518 }
2519
2520 if (ether_frame->ether_dhost[0] & 0x01) {
2521 if (opts & MAC_ALLMCAST) {
2522 adapter->rcv_multicasts++;
2523 adapter->stats.multicast++;
b574488e 2524 return true;
4d6f6af8
GKH
2525 }
2526 if (opts & MAC_MCAST) {
e9eff9d6 2527 struct mcast_address *mcaddr = adapter->mcastaddrs;
4d6f6af8
GKH
2528
2529 while (mcaddr) {
2530 ETHER_EQ_ADDR(mcaddr->address,
2531 ether_frame->ether_dhost,
2532 equaladdr);
2533 if (equaladdr) {
2534 adapter->rcv_multicasts++;
2535 adapter->stats.multicast++;
b574488e 2536 return true;
4d6f6af8
GKH
2537 }
2538 mcaddr = mcaddr->next;
2539 }
b574488e 2540 return false;
4d6f6af8 2541 } else {
b574488e 2542 return false;
4d6f6af8
GKH
2543 }
2544 }
2545 if (opts & MAC_DIRECTED) {
2546 adapter->rcv_unicasts++;
b574488e 2547 return true;
4d6f6af8 2548 }
b574488e 2549 return false;
4d6f6af8
GKH
2550
2551}
2552
e9eff9d6 2553static int slic_mac_set_address(struct net_device *dev, void *ptr)
4d6f6af8 2554{
e9eff9d6 2555 struct adapter *adapter = (struct adapter *)netdev_priv(dev);
4d6f6af8
GKH
2556 struct sockaddr *addr = ptr;
2557
4d6f6af8
GKH
2558 if (netif_running(dev))
2559 return -EBUSY;
2560 if (!adapter)
2561 return -EBUSY;
e8bc9b7a 2562
4d6f6af8
GKH
2563 memcpy(dev->dev_addr, addr->sa_data, dev->addr_len);
2564 memcpy(adapter->currmacaddr, addr->sa_data, dev->addr_len);
4d6f6af8 2565
b574488e 2566 slic_config_set(adapter, true);
4d6f6af8
GKH
2567 return 0;
2568}
2569
e9eff9d6 2570static void slic_timer_load_check(ulong cardaddr)
4d6f6af8 2571{
e9eff9d6
LD
2572 struct sliccard *card = (struct sliccard *)cardaddr;
2573 struct adapter *adapter = card->master;
62f691a3 2574 u32 __iomem *intagg;
e9eff9d6
LD
2575 u32 load = card->events;
2576 u32 level = 0;
4d6f6af8 2577
62f691a3
GKH
2578 intagg = &adapter->slic_regs->slic_intagg;
2579
4d6f6af8
GKH
2580 if ((adapter) && (adapter->state == ADAPT_UP) &&
2581 (card->state == CARD_UP) && (slic_global.dynamic_intagg)) {
2582 if (adapter->devid == SLIC_1GB_DEVICE_ID) {
2583 if (adapter->linkspeed == LINK_1000MB)
2584 level = 100;
2585 else {
2586 if (load > SLIC_LOAD_5)
2587 level = SLIC_INTAGG_5;
2588 else if (load > SLIC_LOAD_4)
2589 level = SLIC_INTAGG_4;
2590 else if (load > SLIC_LOAD_3)
2591 level = SLIC_INTAGG_3;
2592 else if (load > SLIC_LOAD_2)
2593 level = SLIC_INTAGG_2;
2594 else if (load > SLIC_LOAD_1)
2595 level = SLIC_INTAGG_1;
2596 else
2597 level = SLIC_INTAGG_0;
2598 }
2599 if (card->loadlevel_current != level) {
2600 card->loadlevel_current = level;
62f691a3 2601 slic_reg32_write(intagg, level, FLUSH);
4d6f6af8
GKH
2602 }
2603 } else {
2604 if (load > SLIC_LOAD_5)
2605 level = SLIC_INTAGG_5;
2606 else if (load > SLIC_LOAD_4)
2607 level = SLIC_INTAGG_4;
2608 else if (load > SLIC_LOAD_3)
2609 level = SLIC_INTAGG_3;
2610 else if (load > SLIC_LOAD_2)
2611 level = SLIC_INTAGG_2;
2612 else if (load > SLIC_LOAD_1)
2613 level = SLIC_INTAGG_1;
2614 else
2615 level = SLIC_INTAGG_0;
2616 if (card->loadlevel_current != level) {
2617 card->loadlevel_current = level;
62f691a3 2618 slic_reg32_write(intagg, level, FLUSH);
4d6f6af8
GKH
2619 }
2620 }
2621 }
2622 card->events = 0;
db7a673a 2623 card->loadtimer.expires = jiffies + (SLIC_LOADTIMER_PERIOD * HZ);
4d6f6af8
GKH
2624 add_timer(&card->loadtimer);
2625}
2626
e9eff9d6 2627static void slic_assert_fail(void)
4d6f6af8 2628{
e9eff9d6
LD
2629 u32 cpuid;
2630 u32 curr_pid;
4d6f6af8
GKH
2631 cpuid = smp_processor_id();
2632 curr_pid = current->pid;
2633
2634 DBG_ERROR("%s CPU # %d ---- PID # %d\n", __func__, cpuid, curr_pid);
2635}
2636
e9eff9d6
LD
2637static int slic_upr_queue_request(struct adapter *adapter,
2638 u32 upr_request,
2639 u32 upr_data,
2640 u32 upr_data_h,
2641 u32 upr_buffer, u32 upr_buffer_h)
4d6f6af8 2642{
e9eff9d6
LD
2643 struct slic_upr *upr;
2644 struct slic_upr *uprqueue;
4d6f6af8 2645
e9eff9d6 2646 upr = kmalloc(sizeof(struct slic_upr), GFP_ATOMIC);
e8bc9b7a 2647 if (!upr)
4d6f6af8 2648 return -ENOMEM;
e8bc9b7a 2649
4d6f6af8
GKH
2650 upr->adapter = adapter->port;
2651 upr->upr_request = upr_request;
2652 upr->upr_data = upr_data;
2653 upr->upr_buffer = upr_buffer;
2654 upr->upr_data_h = upr_data_h;
2655 upr->upr_buffer_h = upr_buffer_h;
2656 upr->next = NULL;
2657 if (adapter->upr_list) {
2658 uprqueue = adapter->upr_list;
2659
2660 while (uprqueue->next)
2661 uprqueue = uprqueue->next;
2662 uprqueue->next = upr;
2663 } else {
2664 adapter->upr_list = upr;
2665 }
2666 return STATUS_SUCCESS;
2667}
2668
e9eff9d6
LD
2669static int slic_upr_request(struct adapter *adapter,
2670 u32 upr_request,
2671 u32 upr_data,
2672 u32 upr_data_h,
2673 u32 upr_buffer, u32 upr_buffer_h)
4d6f6af8
GKH
2674{
2675 int status;
2676
e9eff9d6 2677 spin_lock_irqsave(&adapter->upr_lock.lock, adapter->upr_lock.flags);
4d6f6af8
GKH
2678 status = slic_upr_queue_request(adapter,
2679 upr_request,
2680 upr_data,
2681 upr_data_h, upr_buffer, upr_buffer_h);
2682 if (status != STATUS_SUCCESS) {
e9eff9d6
LD
2683 spin_unlock_irqrestore(&adapter->upr_lock.lock,
2684 adapter->upr_lock.flags);
4d6f6af8
GKH
2685 return status;
2686 }
2687 slic_upr_start(adapter);
e9eff9d6
LD
2688 spin_unlock_irqrestore(&adapter->upr_lock.lock,
2689 adapter->upr_lock.flags);
4d6f6af8
GKH
2690 return STATUS_PENDING;
2691}
2692
e9eff9d6 2693static void slic_upr_request_complete(struct adapter *adapter, u32 isr)
4d6f6af8 2694{
e9eff9d6
LD
2695 struct sliccard *card = adapter->card;
2696 struct slic_upr *upr;
4d6f6af8 2697
e9eff9d6 2698 spin_lock_irqsave(&adapter->upr_lock.lock, adapter->upr_lock.flags);
4d6f6af8
GKH
2699 upr = adapter->upr_list;
2700 if (!upr) {
2701 ASSERT(0);
e9eff9d6
LD
2702 spin_unlock_irqrestore(&adapter->upr_lock.lock,
2703 adapter->upr_lock.flags);
4d6f6af8
GKH
2704 return;
2705 }
2706 adapter->upr_list = upr->next;
2707 upr->next = NULL;
2708 adapter->upr_busy = 0;
2709 ASSERT(adapter->port == upr->adapter);
2710 switch (upr->upr_request) {
2711 case SLIC_UPR_STATS:
2712 {
e9eff9d6
LD
2713 struct slic_stats *slicstats =
2714 (struct slic_stats *) &adapter->pshmem->inicstats;
2715 struct slic_stats *newstats = slicstats;
2716 struct slic_stats *old = &adapter->inicstats_prev;
2717 struct slicnet_stats *stst = &adapter->slic_stats;
3467db10 2718
4d6f6af8
GKH
2719 if (isr & ISR_UPCERR) {
2720 DBG_ERROR
2721 ("SLIC_UPR_STATS command failed isr[%x]\n",
2722 isr);
2723
2724 break;
2725 }
4d6f6af8
GKH
2726 UPDATE_STATS_GB(stst->tcp.xmit_tcp_segs,
2727 newstats->xmit_tcp_segs_gb,
2728 old->xmit_tcp_segs_gb);
2729
2730 UPDATE_STATS_GB(stst->tcp.xmit_tcp_bytes,
2731 newstats->xmit_tcp_bytes_gb,
2732 old->xmit_tcp_bytes_gb);
2733
2734 UPDATE_STATS_GB(stst->tcp.rcv_tcp_segs,
2735 newstats->rcv_tcp_segs_gb,
2736 old->rcv_tcp_segs_gb);
2737
2738 UPDATE_STATS_GB(stst->tcp.rcv_tcp_bytes,
2739 newstats->rcv_tcp_bytes_gb,
2740 old->rcv_tcp_bytes_gb);
2741
2742 UPDATE_STATS_GB(stst->iface.xmt_bytes,
2743 newstats->xmit_bytes_gb,
2744 old->xmit_bytes_gb);
2745
2746 UPDATE_STATS_GB(stst->iface.xmt_ucast,
2747 newstats->xmit_unicasts_gb,
2748 old->xmit_unicasts_gb);
2749
2750 UPDATE_STATS_GB(stst->iface.rcv_bytes,
2751 newstats->rcv_bytes_gb,
2752 old->rcv_bytes_gb);
2753
2754 UPDATE_STATS_GB(stst->iface.rcv_ucast,
2755 newstats->rcv_unicasts_gb,
2756 old->rcv_unicasts_gb);
2757
2758 UPDATE_STATS_GB(stst->iface.xmt_errors,
2759 newstats->xmit_collisions_gb,
2760 old->xmit_collisions_gb);
2761
2762 UPDATE_STATS_GB(stst->iface.xmt_errors,
2763 newstats->xmit_excess_collisions_gb,
2764 old->xmit_excess_collisions_gb);
2765
2766 UPDATE_STATS_GB(stst->iface.xmt_errors,
2767 newstats->xmit_other_error_gb,
2768 old->xmit_other_error_gb);
2769
2770 UPDATE_STATS_GB(stst->iface.rcv_errors,
2771 newstats->rcv_other_error_gb,
2772 old->rcv_other_error_gb);
2773
2774 UPDATE_STATS_GB(stst->iface.rcv_discards,
2775 newstats->rcv_drops_gb,
2776 old->rcv_drops_gb);
2777
2778 if (newstats->rcv_drops_gb > old->rcv_drops_gb) {
2779 adapter->rcv_drops +=
2780 (newstats->rcv_drops_gb -
2781 old->rcv_drops_gb);
2782 }
e9eff9d6 2783 memcpy(old, newstats, sizeof(struct slic_stats));
4d6f6af8
GKH
2784 break;
2785 }
2786 case SLIC_UPR_RLSR:
2787 slic_link_upr_complete(adapter, isr);
2788 break;
2789 case SLIC_UPR_RCONFIG:
2790 break;
2791 case SLIC_UPR_RPHY:
2792 ASSERT(0);
2793 break;
2794 case SLIC_UPR_ENLB:
2795 ASSERT(0);
2796 break;
2797 case SLIC_UPR_ENCT:
2798 ASSERT(0);
2799 break;
2800 case SLIC_UPR_PDWN:
2801 ASSERT(0);
2802 break;
2803 case SLIC_UPR_PING:
2804 card->pingstatus |= (isr & ISR_PINGDSMASK);
2805 break;
4d6f6af8
GKH
2806 default:
2807 ASSERT(0);
2808 }
e9eff9d6 2809 kfree(upr);
4d6f6af8 2810 slic_upr_start(adapter);
e9eff9d6
LD
2811 spin_unlock_irqrestore(&adapter->upr_lock.lock,
2812 adapter->upr_lock.flags);
4d6f6af8
GKH
2813}
2814
e9eff9d6 2815static void slic_upr_start(struct adapter *adapter)
4d6f6af8 2816{
e9eff9d6
LD
2817 struct slic_upr *upr;
2818 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
4d6f6af8
GKH
2819/*
2820 char * ptr1;
2821 char * ptr2;
2822 uint cmdoffset;
2823*/
2824 upr = adapter->upr_list;
2825 if (!upr)
2826 return;
2827 if (adapter->upr_busy)
2828 return;
2829 adapter->upr_busy = 1;
2830
2831 switch (upr->upr_request) {
2832 case SLIC_UPR_STATS:
2833 if (upr->upr_data_h == 0) {
62f691a3
GKH
2834 slic_reg32_write(&slic_regs->slic_stats, upr->upr_data,
2835 FLUSH);
4d6f6af8 2836 } else {
28980a3c
GKH
2837 slic_reg64_write(adapter, &slic_regs->slic_stats64,
2838 upr->upr_data,
2839 &slic_regs->slic_addr_upper,
2840 upr->upr_data_h, FLUSH);
4d6f6af8
GKH
2841 }
2842 break;
2843
2844 case SLIC_UPR_RLSR:
28980a3c
GKH
2845 slic_reg64_write(adapter, &slic_regs->slic_rlsr, upr->upr_data,
2846 &slic_regs->slic_addr_upper, upr->upr_data_h,
2847 FLUSH);
4d6f6af8
GKH
2848 break;
2849
2850 case SLIC_UPR_RCONFIG:
28980a3c
GKH
2851 slic_reg64_write(adapter, &slic_regs->slic_rconfig,
2852 upr->upr_data, &slic_regs->slic_addr_upper,
2853 upr->upr_data_h, FLUSH);
4d6f6af8 2854 break;
4d6f6af8 2855 case SLIC_UPR_PING:
62f691a3 2856 slic_reg32_write(&slic_regs->slic_ping, 1, FLUSH);
4d6f6af8
GKH
2857 break;
2858 default:
2859 ASSERT(0);
2860 }
2861}
2862
e9eff9d6 2863static void slic_link_upr_complete(struct adapter *adapter, u32 isr)
4d6f6af8 2864{
e9eff9d6 2865 u32 linkstatus = adapter->pshmem->linkstatus;
4d6f6af8 2866 uint linkup;
e9eff9d6
LD
2867 unsigned char linkspeed;
2868 unsigned char linkduplex;
4d6f6af8 2869
4d6f6af8 2870 if ((isr & ISR_UPCERR) || (isr & ISR_UPCBSY)) {
e9eff9d6 2871 struct slic_shmem *pshmem;
4d6f6af8 2872
e9eff9d6 2873 pshmem = (struct slic_shmem *)adapter->phys_shmem;
4d6f6af8
GKH
2874#if defined(CONFIG_X86_64)
2875 slic_upr_queue_request(adapter,
2876 SLIC_UPR_RLSR,
2877 SLIC_GET_ADDR_LOW(&pshmem->linkstatus),
2878 SLIC_GET_ADDR_HIGH(&pshmem->linkstatus),
2879 0, 0);
2880#elif defined(CONFIG_X86)
2881 slic_upr_queue_request(adapter,
2882 SLIC_UPR_RLSR,
e9eff9d6 2883 (u32) &pshmem->linkstatus,
4d6f6af8
GKH
2884 SLIC_GET_ADDR_HIGH(pshmem), 0, 0);
2885#else
2886 Stop Compilation;
2887#endif
2888 return;
2889 }
2890 if (adapter->state != ADAPT_UP)
2891 return;
2892
2893 ASSERT((adapter->devid == SLIC_1GB_DEVICE_ID)
2894 || (adapter->devid == SLIC_2GB_DEVICE_ID));
2895
2896 linkup = linkstatus & GIG_LINKUP ? LINK_UP : LINK_DOWN;
e8bc9b7a 2897 if (linkstatus & GIG_SPEED_1000)
4d6f6af8 2898 linkspeed = LINK_1000MB;
e8bc9b7a 2899 else if (linkstatus & GIG_SPEED_100)
4d6f6af8 2900 linkspeed = LINK_100MB;
e8bc9b7a 2901 else
4d6f6af8 2902 linkspeed = LINK_10MB;
e8bc9b7a
GKH
2903
2904 if (linkstatus & GIG_FULLDUPLEX)
4d6f6af8 2905 linkduplex = LINK_FULLD;
e8bc9b7a 2906 else
4d6f6af8 2907 linkduplex = LINK_HALFD;
4d6f6af8 2908
e8bc9b7a 2909 if ((adapter->linkstate == LINK_DOWN) && (linkup == LINK_DOWN))
4d6f6af8 2910 return;
4d6f6af8
GKH
2911
2912 /* link up event, but nothing has changed */
2913 if ((adapter->linkstate == LINK_UP) &&
2914 (linkup == LINK_UP) &&
2915 (adapter->linkspeed == linkspeed) &&
e8bc9b7a 2916 (adapter->linkduplex == linkduplex))
4d6f6af8 2917 return;
4d6f6af8
GKH
2918
2919 /* link has changed at this point */
2920
2921 /* link has gone from up to down */
2922 if (linkup == LINK_DOWN) {
2923 adapter->linkstate = LINK_DOWN;
4d6f6af8
GKH
2924 return;
2925 }
2926
2927 /* link has gone from down to up */
2928 adapter->linkspeed = linkspeed;
2929 adapter->linkduplex = linkduplex;
2930
2931 if (adapter->linkstate != LINK_UP) {
2932 /* setup the mac */
b574488e 2933 slic_config_set(adapter, true);
4d6f6af8 2934 adapter->linkstate = LINK_UP;
77faefa3 2935 netif_start_queue(adapter->netdev);
4d6f6af8 2936 }
4d6f6af8
GKH
2937}
2938
2939/*
2940 * this is here to checksum the eeprom, there is some ucode bug
2941 * which prevens us from using the ucode result.
2942 * remove this once ucode is fixed.
2943 */
e9eff9d6 2944static ushort slic_eeprom_cksum(char *m, int len)
4d6f6af8
GKH
2945{
2946#define ADDCARRY(x) (x > 65535 ? x -= 65535 : x)
2947#define REDUCE {l_util.l = sum; sum = l_util.s[0] + l_util.s[1]; ADDCARRY(sum);\
2948 }
2949
e9eff9d6
LD
2950 u16 *w;
2951 u32 sum = 0;
2952 u32 byte_swapped = 0;
2953 u32 w_int;
4d6f6af8
GKH
2954
2955 union {
2956 char c[2];
2957 ushort s;
2958 } s_util;
2959
2960 union {
2961 ushort s[2];
2962 int l;
2963 } l_util;
2964
2965 l_util.l = 0;
2966 s_util.s = 0;
2967
e9eff9d6 2968 w = (u16 *)m;
4d6f6af8 2969#ifdef CONFIG_X86_64
e9eff9d6 2970 w_int = (u32) ((ulong) w & 0x00000000FFFFFFFF);
4d6f6af8 2971#else
e9eff9d6 2972 w_int = (u32) (w);
4d6f6af8
GKH
2973#endif
2974 if ((1 & w_int) && (len > 0)) {
2975 REDUCE;
2976 sum <<= 8;
e9eff9d6
LD
2977 s_util.c[0] = *(unsigned char *)w;
2978 w = (u16 *)((char *)w + 1);
4d6f6af8
GKH
2979 len--;
2980 byte_swapped = 1;
2981 }
2982
2983 /* Unroll the loop to make overhead from branches &c small. */
2984 while ((len -= 32) >= 0) {
2985 sum += w[0];
2986 sum += w[1];
2987 sum += w[2];
2988 sum += w[3];
2989 sum += w[4];
2990 sum += w[5];
2991 sum += w[6];
2992 sum += w[7];
2993 sum += w[8];
2994 sum += w[9];
2995 sum += w[10];
2996 sum += w[11];
2997 sum += w[12];
2998 sum += w[13];
2999 sum += w[14];
3000 sum += w[15];
e9eff9d6 3001 w = (u16 *)((ulong) w + 16); /* verify */
4d6f6af8
GKH
3002 }
3003 len += 32;
3004 while ((len -= 8) >= 0) {
3005 sum += w[0];
3006 sum += w[1];
3007 sum += w[2];
3008 sum += w[3];
e9eff9d6 3009 w = (u16 *)((ulong) w + 4); /* verify */
4d6f6af8
GKH
3010 }
3011 len += 8;
3012 if (len != 0 || byte_swapped != 0) {
3013 REDUCE;
3014 while ((len -= 2) >= 0)
3015 sum += *w++; /* verify */
3016 if (byte_swapped) {
3017 REDUCE;
3018 sum <<= 8;
3019 byte_swapped = 0;
3020 if (len == -1) {
e9eff9d6 3021 s_util.c[1] = *(char *) w;
4d6f6af8
GKH
3022 sum += s_util.s;
3023 len = 0;
3024 } else {
3025 len = -1;
3026 }
3027
3028 } else if (len == -1) {
e9eff9d6 3029 s_util.c[0] = *(char *) w;
4d6f6af8
GKH
3030 }
3031
3032 if (len == -1) {
3033 s_util.c[1] = 0;
3034 sum += s_util.s;
3035 }
3036 }
3037 REDUCE;
3038 return (ushort) sum;
3039}
3040
e9eff9d6 3041static int slic_rspqueue_init(struct adapter *adapter)
4d6f6af8
GKH
3042{
3043 int i;
e9eff9d6
LD
3044 struct slic_rspqueue *rspq = &adapter->rspqueue;
3045 __iomem struct slic_regs *slic_regs = adapter->slic_regs;
3046 u32 paddrh = 0;
4d6f6af8 3047
4d6f6af8 3048 ASSERT(adapter->state == ADAPT_DOWN);
e9eff9d6 3049 memset(rspq, 0, sizeof(struct slic_rspqueue));
4d6f6af8
GKH
3050
3051 rspq->num_pages = SLIC_RSPQ_PAGES_GB;
3052
3053 for (i = 0; i < rspq->num_pages; i++) {
3054 rspq->vaddr[i] =
3055 pci_alloc_consistent(adapter->pcidev, PAGE_SIZE,
3056 &rspq->paddr[i]);
3057 if (!rspq->vaddr[i]) {
3058 DBG_ERROR
3059 ("rspqueue_init_failed pci_alloc_consistent\n");
3060 slic_rspqueue_free(adapter);
3061 return STATUS_FAILURE;
3062 }
3063#ifndef CONFIG_X86_64
e9eff9d6
LD
3064 ASSERT(((u32) rspq->vaddr[i] & 0xFFFFF000) ==
3065 (u32) rspq->vaddr[i]);
3066 ASSERT(((u32) rspq->paddr[i] & 0xFFFFF000) ==
3067 (u32) rspq->paddr[i]);
4d6f6af8 3068#endif
e9eff9d6 3069 memset(rspq->vaddr[i], 0, PAGE_SIZE);
4d6f6af8
GKH
3070
3071 if (paddrh == 0) {
62f691a3
GKH
3072 slic_reg32_write(&slic_regs->slic_rbar,
3073 (rspq->paddr[i] | SLIC_RSPQ_BUFSINPAGE),
3074 DONT_FLUSH);
4d6f6af8 3075 } else {
28980a3c
GKH
3076 slic_reg64_write(adapter, &slic_regs->slic_rbar64,
3077 (rspq->paddr[i] | SLIC_RSPQ_BUFSINPAGE),
3078 &slic_regs->slic_addr_upper,
3079 paddrh, DONT_FLUSH);
4d6f6af8
GKH
3080 }
3081 }
3082 rspq->offset = 0;
3083 rspq->pageindex = 0;
e9eff9d6 3084 rspq->rspbuf = (struct slic_rspbuf *)rspq->vaddr[0];
4d6f6af8
GKH
3085 return STATUS_SUCCESS;
3086}
3087
e9eff9d6 3088static void slic_rspqueue_free(struct adapter *adapter)
4d6f6af8
GKH
3089{
3090 int i;
e9eff9d6 3091 struct slic_rspqueue *rspq = &adapter->rspqueue;
4d6f6af8 3092
4d6f6af8
GKH
3093 for (i = 0; i < rspq->num_pages; i++) {
3094 if (rspq->vaddr[i]) {
4d6f6af8
GKH
3095 pci_free_consistent(adapter->pcidev, PAGE_SIZE,
3096 rspq->vaddr[i], rspq->paddr[i]);
3097 }
3098 rspq->vaddr[i] = NULL;
3099 rspq->paddr[i] = 0;
3100 }
3101 rspq->offset = 0;
3102 rspq->pageindex = 0;
3103 rspq->rspbuf = NULL;
3104}
3105
e9eff9d6 3106static struct slic_rspbuf *slic_rspqueue_getnext(struct adapter *adapter)
4d6f6af8 3107{
e9eff9d6
LD
3108 struct slic_rspqueue *rspq = &adapter->rspqueue;
3109 struct slic_rspbuf *buf;
4d6f6af8
GKH
3110
3111 if (!(rspq->rspbuf->status))
3112 return NULL;
3113
3114 buf = rspq->rspbuf;
3115#ifndef CONFIG_X86_64
3116 ASSERT((buf->status & 0xFFFFFFE0) == 0);
3117#endif
3118 ASSERT(buf->hosthandle);
3119 if (++rspq->offset < SLIC_RSPQ_BUFSINPAGE) {
3120 rspq->rspbuf++;
3121#ifndef CONFIG_X86_64
e9eff9d6
LD
3122 ASSERT(((u32) rspq->rspbuf & 0xFFFFFFE0) ==
3123 (u32) rspq->rspbuf);
4d6f6af8
GKH
3124#endif
3125 } else {
3126 ASSERT(rspq->offset == SLIC_RSPQ_BUFSINPAGE);
28980a3c
GKH
3127 slic_reg64_write(adapter, &adapter->slic_regs->slic_rbar64,
3128 (rspq->paddr[rspq->pageindex] | SLIC_RSPQ_BUFSINPAGE),
3129 &adapter->slic_regs->slic_addr_upper, 0, DONT_FLUSH);
4d6f6af8
GKH
3130 rspq->pageindex = (++rspq->pageindex) % rspq->num_pages;
3131 rspq->offset = 0;
e9eff9d6
LD
3132 rspq->rspbuf = (struct slic_rspbuf *)
3133 rspq->vaddr[rspq->pageindex];
4d6f6af8 3134#ifndef CONFIG_X86_64
e9eff9d6
LD
3135 ASSERT(((u32) rspq->rspbuf & 0xFFFFF000) ==
3136 (u32) rspq->rspbuf);
4d6f6af8
GKH
3137#endif
3138 }
3139#ifndef CONFIG_X86_64
e9eff9d6 3140 ASSERT(((u32) buf & 0xFFFFFFE0) == (u32) buf);
4d6f6af8
GKH
3141#endif
3142 return buf;
3143}
3144
e9eff9d6 3145static void slic_cmdqmem_init(struct adapter *adapter)
4d6f6af8 3146{
e9eff9d6 3147 struct slic_cmdqmem *cmdqmem = &adapter->cmdqmem;
4d6f6af8 3148
e9eff9d6 3149 memset(cmdqmem, 0, sizeof(struct slic_cmdqmem));
4d6f6af8
GKH
3150}
3151
e9eff9d6 3152static void slic_cmdqmem_free(struct adapter *adapter)
4d6f6af8 3153{
e9eff9d6 3154 struct slic_cmdqmem *cmdqmem = &adapter->cmdqmem;
4d6f6af8
GKH
3155 int i;
3156
4d6f6af8
GKH
3157 for (i = 0; i < SLIC_CMDQ_MAXPAGES; i++) {
3158 if (cmdqmem->pages[i]) {
4d6f6af8
GKH
3159 pci_free_consistent(adapter->pcidev,
3160 PAGE_SIZE,
e9eff9d6 3161 (void *) cmdqmem->pages[i],
4d6f6af8
GKH
3162 cmdqmem->dma_pages[i]);
3163 }
3164 }
e9eff9d6 3165 memset(cmdqmem, 0, sizeof(struct slic_cmdqmem));
4d6f6af8
GKH
3166}
3167
e9eff9d6 3168static u32 *slic_cmdqmem_addpage(struct adapter *adapter)
4d6f6af8 3169{
e9eff9d6
LD
3170 struct slic_cmdqmem *cmdqmem = &adapter->cmdqmem;
3171 u32 *pageaddr;
4d6f6af8
GKH
3172
3173 if (cmdqmem->pagecnt >= SLIC_CMDQ_MAXPAGES)
3174 return NULL;
3175 pageaddr = pci_alloc_consistent(adapter->pcidev,
3176 PAGE_SIZE,
3177 &cmdqmem->dma_pages[cmdqmem->pagecnt]);
3178 if (!pageaddr)
3179 return NULL;
3180#ifndef CONFIG_X86_64
e9eff9d6 3181 ASSERT(((u32) pageaddr & 0xFFFFF000) == (u32) pageaddr);
4d6f6af8
GKH
3182#endif
3183 cmdqmem->pages[cmdqmem->pagecnt] = pageaddr;
3184 cmdqmem->pagecnt++;
3185 return pageaddr;
3186}
3187
e9eff9d6 3188static int slic_cmdq_init(struct adapter *adapter)
4d6f6af8
GKH
3189{
3190 int i;
e9eff9d6 3191 u32 *pageaddr;
4d6f6af8 3192
4d6f6af8 3193 ASSERT(adapter->state == ADAPT_DOWN);
e9eff9d6
LD
3194 memset(&adapter->cmdq_all, 0, sizeof(struct slic_cmdqueue));
3195 memset(&adapter->cmdq_free, 0, sizeof(struct slic_cmdqueue));
3196 memset(&adapter->cmdq_done, 0, sizeof(struct slic_cmdqueue));
3197 spin_lock_init(&adapter->cmdq_all.lock.lock);
3198 spin_lock_init(&adapter->cmdq_free.lock.lock);
3199 spin_lock_init(&adapter->cmdq_done.lock.lock);
4d6f6af8
GKH
3200 slic_cmdqmem_init(adapter);
3201 adapter->slic_handle_ix = 1;
3202 for (i = 0; i < SLIC_CMDQ_INITPAGES; i++) {
3203 pageaddr = slic_cmdqmem_addpage(adapter);
3204#ifndef CONFIG_X86_64
e9eff9d6 3205 ASSERT(((u32) pageaddr & 0xFFFFF000) == (u32) pageaddr);
4d6f6af8
GKH
3206#endif
3207 if (!pageaddr) {
3208 slic_cmdq_free(adapter);
3209 return STATUS_FAILURE;
3210 }
3211 slic_cmdq_addcmdpage(adapter, pageaddr);
3212 }
3213 adapter->slic_handle_ix = 1;
4d6f6af8
GKH
3214
3215 return STATUS_SUCCESS;
3216}
3217
e9eff9d6 3218static void slic_cmdq_free(struct adapter *adapter)
4d6f6af8 3219{
e9eff9d6 3220 struct slic_hostcmd *cmd;
4d6f6af8 3221
4d6f6af8
GKH
3222 cmd = adapter->cmdq_all.head;
3223 while (cmd) {
3224 if (cmd->busy) {
3225 struct sk_buff *tempskb;
3226
3227 tempskb = cmd->skb;
3228 if (tempskb) {
3229 cmd->skb = NULL;
3230 dev_kfree_skb_irq(tempskb);
3231 }
3232 }
3233 cmd = cmd->next_all;
3234 }
e9eff9d6
LD
3235 memset(&adapter->cmdq_all, 0, sizeof(struct slic_cmdqueue));
3236 memset(&adapter->cmdq_free, 0, sizeof(struct slic_cmdqueue));
3237 memset(&adapter->cmdq_done, 0, sizeof(struct slic_cmdqueue));
4d6f6af8
GKH
3238 slic_cmdqmem_free(adapter);
3239}
3240
e9eff9d6 3241static void slic_cmdq_reset(struct adapter *adapter)
4d6f6af8 3242{
e9eff9d6 3243 struct slic_hostcmd *hcmd;
4d6f6af8 3244 struct sk_buff *skb;
e9eff9d6 3245 u32 outstanding;
4d6f6af8 3246
e9eff9d6
LD
3247 spin_lock_irqsave(&adapter->cmdq_free.lock.lock,
3248 adapter->cmdq_free.lock.flags);
3249 spin_lock_irqsave(&adapter->cmdq_done.lock.lock,
3250 adapter->cmdq_done.lock.flags);
4d6f6af8
GKH
3251 outstanding = adapter->cmdq_all.count - adapter->cmdq_done.count;
3252 outstanding -= adapter->cmdq_free.count;
3253 hcmd = adapter->cmdq_all.head;
3254 while (hcmd) {
3255 if (hcmd->busy) {
3256 skb = hcmd->skb;
3257 ASSERT(skb);
4d6f6af8
GKH
3258 hcmd->busy = 0;
3259 hcmd->skb = NULL;
4d6f6af8
GKH
3260 dev_kfree_skb_irq(skb);
3261 }
3262 hcmd = hcmd->next_all;
3263 }
3264 adapter->cmdq_free.count = 0;
3265 adapter->cmdq_free.head = NULL;
3266 adapter->cmdq_free.tail = NULL;
3267 adapter->cmdq_done.count = 0;
3268 adapter->cmdq_done.head = NULL;
3269 adapter->cmdq_done.tail = NULL;
3270 adapter->cmdq_free.head = adapter->cmdq_all.head;
3271 hcmd = adapter->cmdq_all.head;
3272 while (hcmd) {
3273 adapter->cmdq_free.count++;
3274 hcmd->next = hcmd->next_all;
3275 hcmd = hcmd->next_all;
3276 }
3277 if (adapter->cmdq_free.count != adapter->cmdq_all.count) {
3278 DBG_ERROR("%s free_count %d != all count %d\n", __func__,
3279 adapter->cmdq_free.count, adapter->cmdq_all.count);
3280 }
e9eff9d6
LD
3281 spin_unlock_irqrestore(&adapter->cmdq_done.lock.lock,
3282 adapter->cmdq_done.lock.flags);
3283 spin_unlock_irqrestore(&adapter->cmdq_free.lock.lock,
3284 adapter->cmdq_free.lock.flags);
4d6f6af8
GKH
3285}
3286
e9eff9d6 3287static void slic_cmdq_addcmdpage(struct adapter *adapter, u32 *page)
4d6f6af8 3288{
e9eff9d6
LD
3289 struct slic_hostcmd *cmd;
3290 struct slic_hostcmd *prev;
3291 struct slic_hostcmd *tail;
3292 struct slic_cmdqueue *cmdq;
4d6f6af8 3293 int cmdcnt;
e9eff9d6 3294 void *cmdaddr;
4d6f6af8 3295 ulong phys_addr;
e9eff9d6
LD
3296 u32 phys_addrl;
3297 u32 phys_addrh;
3298 struct slic_handle *pslic_handle;
4d6f6af8
GKH
3299
3300 cmdaddr = page;
e9eff9d6 3301 cmd = (struct slic_hostcmd *)cmdaddr;
4d6f6af8
GKH
3302 cmdcnt = 0;
3303
e9eff9d6 3304 phys_addr = virt_to_bus((void *)page);
4d6f6af8
GKH
3305 phys_addrl = SLIC_GET_ADDR_LOW(phys_addr);
3306 phys_addrh = SLIC_GET_ADDR_HIGH(phys_addr);
3307
3308 prev = NULL;
3309 tail = cmd;
3310 while ((cmdcnt < SLIC_CMDQ_CMDSINPAGE) &&
3311 (adapter->slic_handle_ix < 256)) {
3312 /* Allocate and initialize a SLIC_HANDLE for this command */
3313 SLIC_GET_SLIC_HANDLE(adapter, pslic_handle);
3314 if (pslic_handle == NULL)
3315 ASSERT(0);
3316 ASSERT(pslic_handle ==
3317 &adapter->slic_handles[pslic_handle->token.
3318 handle_index]);
3319 pslic_handle->type = SLIC_HANDLE_CMD;
e9eff9d6 3320 pslic_handle->address = (void *) cmd;
4d6f6af8
GKH
3321 pslic_handle->offset = (ushort) adapter->slic_handle_ix++;
3322 pslic_handle->other_handle = NULL;
3323 pslic_handle->next = NULL;
3324
3325 cmd->pslic_handle = pslic_handle;
3326 cmd->cmd64.hosthandle = pslic_handle->token.handle_token;
b574488e 3327 cmd->busy = false;
4d6f6af8
GKH
3328 cmd->paddrl = phys_addrl;
3329 cmd->paddrh = phys_addrh;
3330 cmd->next_all = prev;
3331 cmd->next = prev;
3332 prev = cmd;
3333 phys_addrl += SLIC_HOSTCMD_SIZE;
3334 cmdaddr += SLIC_HOSTCMD_SIZE;
3335
e9eff9d6 3336 cmd = (struct slic_hostcmd *)cmdaddr;
4d6f6af8
GKH
3337 cmdcnt++;
3338 }
3339
3340 cmdq = &adapter->cmdq_all;
3341 cmdq->count += cmdcnt; /* SLIC_CMDQ_CMDSINPAGE; mooktodo */
3342 tail->next_all = cmdq->head;
4d6f6af8
GKH
3343 cmdq->head = prev;
3344 cmdq = &adapter->cmdq_free;
e9eff9d6 3345 spin_lock_irqsave(&cmdq->lock.lock, cmdq->lock.flags);
4d6f6af8
GKH
3346 cmdq->count += cmdcnt; /* SLIC_CMDQ_CMDSINPAGE; mooktodo */
3347 tail->next = cmdq->head;
4d6f6af8 3348 cmdq->head = prev;
e9eff9d6 3349 spin_unlock_irqrestore(&cmdq->lock.lock, cmdq->lock.flags);
4d6f6af8
GKH
3350}
3351
e9eff9d6 3352static struct slic_hostcmd *slic_cmdq_getfree(struct adapter *adapter)
4d6f6af8 3353{
e9eff9d6
LD
3354 struct slic_cmdqueue *cmdq = &adapter->cmdq_free;
3355 struct slic_hostcmd *cmd = NULL;
4d6f6af8
GKH
3356
3357lock_and_retry:
e9eff9d6 3358 spin_lock_irqsave(&cmdq->lock.lock, cmdq->lock.flags);
4d6f6af8
GKH
3359retry:
3360 cmd = cmdq->head;
3361 if (cmd) {
3362 cmdq->head = cmd->next;
3363 cmdq->count--;
e9eff9d6 3364 spin_unlock_irqrestore(&cmdq->lock.lock, cmdq->lock.flags);
4d6f6af8
GKH
3365 } else {
3366 slic_cmdq_getdone(adapter);
3367 cmd = cmdq->head;
3368 if (cmd) {
3369 goto retry;
3370 } else {
e9eff9d6 3371 u32 *pageaddr;
4d6f6af8 3372
e9eff9d6
LD
3373 spin_unlock_irqrestore(&cmdq->lock.lock,
3374 cmdq->lock.flags);
4d6f6af8
GKH
3375 pageaddr = slic_cmdqmem_addpage(adapter);
3376 if (pageaddr) {
3377 slic_cmdq_addcmdpage(adapter, pageaddr);
3378 goto lock_and_retry;
3379 }
3380 }
3381 }
3382 return cmd;
3383}
3384
e9eff9d6 3385static void slic_cmdq_getdone(struct adapter *adapter)
4d6f6af8 3386{
e9eff9d6
LD
3387 struct slic_cmdqueue *done_cmdq = &adapter->cmdq_done;
3388 struct slic_cmdqueue *free_cmdq = &adapter->cmdq_free;
4d6f6af8
GKH
3389
3390 ASSERT(free_cmdq->head == NULL);
e9eff9d6 3391 spin_lock_irqsave(&done_cmdq->lock.lock, done_cmdq->lock.flags);
4d6f6af8
GKH
3392
3393 free_cmdq->head = done_cmdq->head;
3394 free_cmdq->count = done_cmdq->count;
3395 done_cmdq->head = NULL;
3396 done_cmdq->tail = NULL;
3397 done_cmdq->count = 0;
e9eff9d6 3398 spin_unlock_irqrestore(&done_cmdq->lock.lock, done_cmdq->lock.flags);
4d6f6af8
GKH
3399}
3400
e9eff9d6
LD
3401static void slic_cmdq_putdone_irq(struct adapter *adapter,
3402 struct slic_hostcmd *cmd)
4d6f6af8 3403{
e9eff9d6 3404 struct slic_cmdqueue *cmdq = &adapter->cmdq_done;
4d6f6af8 3405
e9eff9d6 3406 spin_lock(&cmdq->lock.lock);
4d6f6af8 3407 cmd->busy = 0;
4d6f6af8 3408 cmd->next = cmdq->head;
4d6f6af8
GKH
3409 cmdq->head = cmd;
3410 cmdq->count++;
3411 if ((adapter->xmitq_full) && (cmdq->count > 10))
3412 netif_wake_queue(adapter->netdev);
e9eff9d6 3413 spin_unlock(&cmdq->lock.lock);
4d6f6af8
GKH
3414}
3415
e9eff9d6 3416static int slic_rcvqueue_init(struct adapter *adapter)
4d6f6af8
GKH
3417{
3418 int i, count;
e9eff9d6 3419 struct slic_rcvqueue *rcvq = &adapter->rcvqueue;
4d6f6af8 3420
4d6f6af8
GKH
3421 ASSERT(adapter->state == ADAPT_DOWN);
3422 rcvq->tail = NULL;
3423 rcvq->head = NULL;
3424 rcvq->size = SLIC_RCVQ_ENTRIES;
3425 rcvq->errors = 0;
3426 rcvq->count = 0;
3427 i = (SLIC_RCVQ_ENTRIES / SLIC_RCVQ_FILLENTRIES);
3428 count = 0;
3429 while (i) {
3430 count += slic_rcvqueue_fill(adapter);
3431 i--;
3432 }
3433 if (rcvq->count < SLIC_RCVQ_MINENTRIES) {
3434 slic_rcvqueue_free(adapter);
3435 return STATUS_FAILURE;
3436 }
4d6f6af8
GKH
3437 return STATUS_SUCCESS;
3438}
3439
e9eff9d6 3440static void slic_rcvqueue_free(struct adapter *adapter)
4d6f6af8 3441{
e9eff9d6 3442 struct slic_rcvqueue *rcvq = &adapter->rcvqueue;
4d6f6af8
GKH
3443 struct sk_buff *skb;
3444
3445 while (rcvq->head) {
3446 skb = rcvq->head;
3447 rcvq->head = rcvq->head->next;
3448 dev_kfree_skb(skb);
3449 }
3450 rcvq->tail = NULL;
3451 rcvq->head = NULL;
3452 rcvq->count = 0;
3453}
3454
e9eff9d6 3455static struct sk_buff *slic_rcvqueue_getnext(struct adapter *adapter)
4d6f6af8 3456{
e9eff9d6 3457 struct slic_rcvqueue *rcvq = &adapter->rcvqueue;
4d6f6af8 3458 struct sk_buff *skb;
e9eff9d6 3459 struct slic_rcvbuf *rcvbuf;
4d6f6af8
GKH
3460 int count;
3461
3462 if (rcvq->count) {
3463 skb = rcvq->head;
e9eff9d6 3464 rcvbuf = (struct slic_rcvbuf *)skb->head;
4d6f6af8
GKH
3465 ASSERT(rcvbuf);
3466
3467 if (rcvbuf->status & IRHDDR_SVALID) {
3468 rcvq->head = rcvq->head->next;
3469 skb->next = NULL;
3470 rcvq->count--;
3471 } else {
3472 skb = NULL;
3473 }
3474 } else {
3475 DBG_ERROR("RcvQ Empty!! adapter[%p] rcvq[%p] count[%x]\n",
3476 adapter, rcvq, rcvq->count);
3477 skb = NULL;
3478 }
3479 while (rcvq->count < SLIC_RCVQ_FILLTHRESH) {
3480 count = slic_rcvqueue_fill(adapter);
3481 if (!count)
3482 break;
3483 }
3484 if (skb)
3485 rcvq->errors = 0;
3486 return skb;
3487}
3488
e9eff9d6 3489static int slic_rcvqueue_fill(struct adapter *adapter)
4d6f6af8 3490{
e9eff9d6
LD
3491 void *paddr;
3492 u32 paddrl;
3493 u32 paddrh;
3494 struct slic_rcvqueue *rcvq = &adapter->rcvqueue;
4d6f6af8
GKH
3495 int i = 0;
3496
3497 while (i < SLIC_RCVQ_FILLENTRIES) {
e9eff9d6 3498 struct slic_rcvbuf *rcvbuf;
4d6f6af8
GKH
3499 struct sk_buff *skb;
3500#ifdef KLUDGE_FOR_4GB_BOUNDARY
3501retry_rcvqfill:
3502#endif
3503 skb = alloc_skb(SLIC_RCVQ_RCVBUFSIZE, GFP_ATOMIC);
3504 if (skb) {
e9eff9d6 3505 paddr = (void *)pci_map_single(adapter->pcidev,
4d6f6af8 3506 skb->data,
e9eff9d6
LD
3507 SLIC_RCVQ_RCVBUFSIZE,
3508 PCI_DMA_FROMDEVICE);
4d6f6af8
GKH
3509 paddrl = SLIC_GET_ADDR_LOW(paddr);
3510 paddrh = SLIC_GET_ADDR_HIGH(paddr);
3511
3512 skb->len = SLIC_RCVBUF_HEADSIZE;
e9eff9d6 3513 rcvbuf = (struct slic_rcvbuf *)skb->head;
4d6f6af8
GKH
3514 rcvbuf->status = 0;
3515 skb->next = NULL;
3516#ifdef KLUDGE_FOR_4GB_BOUNDARY
3517 if (paddrl == 0) {
3518 DBG_ERROR
3519 ("%s: LOW 32bits PHYSICAL ADDRESS == 0 "
3520 "skb[%p] PROBLEM\n"
3521 " skbdata[%p]\n"
3522 " skblen[%x]\n"
3523 " paddr[%p]\n"
3524 " paddrl[%x]\n"
3525 " paddrh[%x]\n", __func__, skb,
3526 skb->data, skb->len, paddr, paddrl,
3527 paddrh);
3528 DBG_ERROR(" rcvq->head[%p]\n"
3529 " rcvq->tail[%p]\n"
3530 " rcvq->count[%x]\n",
3531 rcvq->head, rcvq->tail, rcvq->count);
3532 DBG_ERROR("SKIP THIS SKB!!!!!!!!\n");
3533 goto retry_rcvqfill;
3534 }
3535#else
3536 if (paddrl == 0) {
3537 DBG_ERROR
3538 ("\n\n%s: LOW 32bits PHYSICAL ADDRESS == 0 "
3539 "skb[%p] GIVE TO CARD ANYWAY\n"
3540 " skbdata[%p]\n"
3541 " paddr[%p]\n"
3542 " paddrl[%x]\n"
3543 " paddrh[%x]\n", __func__, skb,
3544 skb->data, paddr, paddrl, paddrh);
3545 }
3546#endif
3547 if (paddrh == 0) {
62f691a3
GKH
3548 slic_reg32_write(&adapter->slic_regs->slic_hbar,
3549 (u32)paddrl, DONT_FLUSH);
4d6f6af8 3550 } else {
28980a3c
GKH
3551 slic_reg64_write(adapter,
3552 &adapter->slic_regs->slic_hbar64,
3553 paddrl,
3554 &adapter->slic_regs->slic_addr_upper,
3555 paddrh, DONT_FLUSH);
4d6f6af8
GKH
3556 }
3557 if (rcvq->head)
3558 rcvq->tail->next = skb;
3559 else
3560 rcvq->head = skb;
3561 rcvq->tail = skb;
3562 rcvq->count++;
3563 i++;
3564 } else {
3565 DBG_ERROR
3566 ("%s slic_rcvqueue_fill could only get [%d] "
3567 "skbuffs\n",
3568 adapter->netdev->name, i);
3569 break;
3570 }
3571 }
3572 return i;
3573}
3574
e9eff9d6 3575static u32 slic_rcvqueue_reinsert(struct adapter *adapter, struct sk_buff *skb)
4d6f6af8 3576{
e9eff9d6
LD
3577 struct slic_rcvqueue *rcvq = &adapter->rcvqueue;
3578 void *paddr;
3579 u32 paddrl;
3580 u32 paddrh;
3581 struct slic_rcvbuf *rcvbuf = (struct slic_rcvbuf *)skb->head;
4d6f6af8
GKH
3582
3583 ASSERT(skb->len == SLIC_RCVBUF_HEADSIZE);
e9eff9d6
LD
3584
3585 paddr = (void *)pci_map_single(adapter->pcidev, skb->head,
3586 SLIC_RCVQ_RCVBUFSIZE, PCI_DMA_FROMDEVICE);
4d6f6af8
GKH
3587 rcvbuf->status = 0;
3588 skb->next = NULL;
3589
3590 paddrl = SLIC_GET_ADDR_LOW(paddr);
3591 paddrh = SLIC_GET_ADDR_HIGH(paddr);
3592
3593 if (paddrl == 0) {
3594 DBG_ERROR
3595 ("%s: LOW 32bits PHYSICAL ADDRESS == 0 skb[%p] PROBLEM\n"
3596 " skbdata[%p]\n" " skblen[%x]\n"
3597 " paddr[%p]\n" " paddrl[%x]\n"
3598 " paddrh[%x]\n", __func__, skb, skb->data,
3599 skb->len, paddr, paddrl, paddrh);
3600 DBG_ERROR(" rcvq->head[%p]\n"
3601 " rcvq->tail[%p]\n"
3602 " rcvq->count[%x]\n", rcvq->head, rcvq->tail,
3603 rcvq->count);
3604 }
3605 if (paddrh == 0) {
62f691a3
GKH
3606 slic_reg32_write(&adapter->slic_regs->slic_hbar, (u32)paddrl,
3607 DONT_FLUSH);
4d6f6af8 3608 } else {
28980a3c
GKH
3609 slic_reg64_write(adapter, &adapter->slic_regs->slic_hbar64,
3610 paddrl, &adapter->slic_regs->slic_addr_upper,
3611 paddrh, DONT_FLUSH);
4d6f6af8
GKH
3612 }
3613 if (rcvq->head)
3614 rcvq->tail->next = skb;
3615 else
3616 rcvq->head = skb;
3617 rcvq->tail = skb;
3618 rcvq->count++;
3619 return rcvq->count;
3620}
3621
3622static int slic_debug_card_show(struct seq_file *seq, void *v)
3623{
3624#ifdef MOOKTODO
3625 int i;
e9eff9d6 3626 struct sliccard *card = seq->private;
68cf95f3 3627 struct slic_config *config = &card->config;
e9eff9d6
LD
3628 unsigned char *fru = (unsigned char *)(&card->config.atk_fru);
3629 unsigned char *oemfru = (unsigned char *)(&card->config.OemFru);
4d6f6af8
GKH
3630#endif
3631
874073ea 3632 seq_printf(seq, "driver_version : %s\n", slic_proc_version);
4d6f6af8
GKH
3633 seq_printf(seq, "Microcode versions: \n");
3634 seq_printf(seq, " Gigabit (gb) : %s %s\n",
3635 MOJAVE_UCODE_VERS_STRING, MOJAVE_UCODE_VERS_DATE);
3636 seq_printf(seq, " Gigabit Receiver : %s %s\n",
3637 GB_RCVUCODE_VERS_STRING, GB_RCVUCODE_VERS_DATE);
3638 seq_printf(seq, "Vendor : %s\n", slic_vendor);
3639 seq_printf(seq, "Product Name : %s\n", slic_product_name);
3640#ifdef MOOKTODO
3641 seq_printf(seq, "VendorId : %4.4X\n",
3642 config->VendorId);
3643 seq_printf(seq, "DeviceId : %4.4X\n",
3644 config->DeviceId);
3645 seq_printf(seq, "RevisionId : %2.2x\n",
3646 config->RevisionId);
3647 seq_printf(seq, "Bus # : %d\n", card->busnumber);
3648 seq_printf(seq, "Device # : %d\n", card->slotnumber);
3649 seq_printf(seq, "Interfaces : %d\n", card->card_size);
3650 seq_printf(seq, " Initialized : %d\n",
3651 card->adapters_activated);
3652 seq_printf(seq, " Allocated : %d\n",
3653 card->adapters_allocated);
3654 ASSERT(card->card_size <= SLIC_NBR_MACS);
3655 for (i = 0; i < card->card_size; i++) {
3656 seq_printf(seq,
3657 " MAC%d : %2.2X %2.2X %2.2X %2.2X %2.2X %2.2X\n",
3658 i, config->macinfo[i].macaddrA[0],
3659 config->macinfo[i].macaddrA[1],
3660 config->macinfo[i].macaddrA[2],
3661 config->macinfo[i].macaddrA[3],
3662 config->macinfo[i].macaddrA[4],
3663 config->macinfo[i].macaddrA[5]);
3664 }
3665 seq_printf(seq, " IF Init State Duplex/Speed irq\n");
3666 seq_printf(seq, " -------------------------------\n");
3667 for (i = 0; i < card->adapters_allocated; i++) {
e9eff9d6 3668 struct adapter *adapter;
4d6f6af8
GKH
3669
3670 adapter = card->adapter[i];
3671 if (adapter) {
3672 seq_printf(seq,
3673 " %d %d %s %s %s 0x%X\n",
3674 adapter->physport, adapter->state,
3675 SLIC_LINKSTATE(adapter->linkstate),
3676 SLIC_DUPLEX(adapter->linkduplex),
3677 SLIC_SPEED(adapter->linkspeed),
3678 (uint) adapter->irq);
3679 }
3680 }
3681 seq_printf(seq, "Generation # : %4.4X\n", card->gennumber);
3682 seq_printf(seq, "RcvQ max entries : %4.4X\n",
3683 SLIC_RCVQ_ENTRIES);
3684 seq_printf(seq, "Ping Status : %8.8X\n",
3685 card->pingstatus);
3686 seq_printf(seq, "Minimum grant : %2.2x\n",
3687 config->MinGrant);
3688 seq_printf(seq, "Maximum Latency : %2.2x\n", config->MaxLat);
3689 seq_printf(seq, "PciStatus : %4.4x\n",
3690 config->Pcistatus);
3691 seq_printf(seq, "Debug Device Id : %4.4x\n",
3692 config->DbgDevId);
3693 seq_printf(seq, "DRAM ROM Function : %4.4x\n",
3694 config->DramRomFn);
3695 seq_printf(seq, "Network interface Pin 1 : %2.2x\n",
3696 config->NetIntPin1);
3697 seq_printf(seq, "Network interface Pin 2 : %2.2x\n",
3698 config->NetIntPin1);
3699 seq_printf(seq, "Network interface Pin 3 : %2.2x\n",
3700 config->NetIntPin1);
3701 seq_printf(seq, "PM capabilities : %4.4X\n",
3702 config->PMECapab);
3703 seq_printf(seq, "Network Clock Controls : %4.4X\n",
3704 config->NwClkCtrls);
3705
3706 switch (config->FruFormat) {
3707 case ATK_FRU_FORMAT:
3708 {
3709 seq_printf(seq,
3710 "Vendor : Alacritech, Inc.\n");
3711 seq_printf(seq,
3712 "Assembly # : %c%c%c%c%c%c\n",
3713 fru[0], fru[1], fru[2], fru[3], fru[4],
3714 fru[5]);
3715 seq_printf(seq,
3716 "Revision # : %c%c\n",
3717 fru[6], fru[7]);
3718
3719 if (config->OEMFruFormat == VENDOR4_FRU_FORMAT) {
3720 seq_printf(seq,
3721 "Serial # : "
3722 "%c%c%c%c%c%c%c%c%c%c%c%c\n",
3723 fru[8], fru[9], fru[10],
3724 fru[11], fru[12], fru[13],
3725 fru[16], fru[17], fru[18],
3726 fru[19], fru[20], fru[21]);
3727 } else {
3728 seq_printf(seq,
3729 "Serial # : "
3730 "%c%c%c%c%c%c%c%c%c%c%c%c%c%c\n",
3731 fru[8], fru[9], fru[10],
3732 fru[11], fru[12], fru[13],
3733 fru[14], fru[15], fru[16],
3734 fru[17], fru[18], fru[19],
3735 fru[20], fru[21]);
3736 }
3737 break;
3738 }
3739
3740 default:
3741 {
3742 seq_printf(seq,
3743 "Vendor : Alacritech, Inc.\n");
3744 seq_printf(seq,
3745 "Serial # : Empty FRU\n");
3746 break;
3747 }
3748 }
3749
3750 switch (config->OEMFruFormat) {
3751 case VENDOR1_FRU_FORMAT:
3752 {
3753 seq_printf(seq, "FRU Information:\n");
3754 seq_printf(seq, " Commodity # : %c\n",
3755 oemfru[0]);
3756 seq_printf(seq,
3757 " Assembly # : %c%c%c%c\n",
3758 oemfru[1], oemfru[2], oemfru[3], oemfru[4]);
3759 seq_printf(seq,
3760 " Revision # : %c%c\n",
3761 oemfru[5], oemfru[6]);
3762 seq_printf(seq,
3763 " Supplier # : %c%c\n",
3764 oemfru[7], oemfru[8]);
3765 seq_printf(seq,
3766 " Date : %c%c\n",
3767 oemfru[9], oemfru[10]);
3768 seq_sprintf(seq,
3769 " Sequence # : %c%c%c\n",
3770 oemfru[11], oemfru[12], oemfru[13]);
3771 break;
3772 }
3773
3774 case VENDOR2_FRU_FORMAT:
3775 {
3776 seq_printf(seq, "FRU Information:\n");
3777 seq_printf(seq,
3778 " Part # : "
3779 "%c%c%c%c%c%c%c%c\n",
3780 oemfru[0], oemfru[1], oemfru[2],
3781 oemfru[3], oemfru[4], oemfru[5],
3782 oemfru[6], oemfru[7]);
3783 seq_printf(seq,
3784 " Supplier # : %c%c%c%c%c\n",
3785 oemfru[8], oemfru[9], oemfru[10],
3786 oemfru[11], oemfru[12]);
3787 seq_printf(seq,
3788 " Date : %c%c%c\n",
3789 oemfru[13], oemfru[14], oemfru[15]);
3790 seq_sprintf(seq,
3791 " Sequence # : %c%c%c%c\n",
3792 oemfru[16], oemfru[17], oemfru[18],
3793 oemfru[19]);
3794 break;
3795 }
3796
3797 case VENDOR3_FRU_FORMAT:
3798 {
3799 seq_printf(seq, "FRU Information:\n");
3800 }
3801
3802 case VENDOR4_FRU_FORMAT:
3803 {
3804 seq_printf(seq, "FRU Information:\n");
3805 seq_printf(seq,
3806 " FRU Number : "
3807 "%c%c%c%c%c%c%c%c\n",
3808 oemfru[0], oemfru[1], oemfru[2],
3809 oemfru[3], oemfru[4], oemfru[5],
3810 oemfru[6], oemfru[7]);
3811 seq_sprintf(seq,
3812 " Part Number : "
3813 "%c%c%c%c%c%c%c%c\n",
3814 oemfru[8], oemfru[9], oemfru[10],
3815 oemfru[11], oemfru[12], oemfru[13],
3816 oemfru[14], oemfru[15]);
3817 seq_printf(seq,
3818 " EC Level : "
3819 "%c%c%c%c%c%c%c%c\n",
3820 oemfru[16], oemfru[17], oemfru[18],
3821 oemfru[19], oemfru[20], oemfru[21],
3822 oemfru[22], oemfru[23]);
3823 break;
3824 }
3825
3826 default:
3827 break;
3828 }
3829#endif
3830
3831 return 0;
3832}
3833
3834static int slic_debug_adapter_show(struct seq_file *seq, void *v)
3835{
e9eff9d6 3836 struct adapter *adapter = seq->private;
4d6f6af8
GKH
3837
3838 if ((adapter->netdev) && (adapter->netdev->name)) {
3839 seq_printf(seq, "info: interface : %s\n",
3840 adapter->netdev->name);
3841 }
3842 seq_printf(seq, "info: status : %s\n",
3843 SLIC_LINKSTATE(adapter->linkstate));
3844 seq_printf(seq, "info: port : %d\n",
3845 adapter->physport);
3846 seq_printf(seq, "info: speed : %s\n",
3847 SLIC_SPEED(adapter->linkspeed));
3848 seq_printf(seq, "info: duplex : %s\n",
3849 SLIC_DUPLEX(adapter->linkduplex));
3850 seq_printf(seq, "info: irq : 0x%X\n",
3851 (uint) adapter->irq);
3852 seq_printf(seq, "info: Interrupt Agg Delay: %d usec\n",
3853 adapter->card->loadlevel_current);
3854 seq_printf(seq, "info: RcvQ max entries : %4.4X\n",
3855 SLIC_RCVQ_ENTRIES);
3856 seq_printf(seq, "info: RcvQ current : %4.4X\n",
3857 adapter->rcvqueue.count);
3858 seq_printf(seq, "rx stats: packets : %8.8lX\n",
3859 adapter->stats.rx_packets);
3860 seq_printf(seq, "rx stats: bytes : %8.8lX\n",
3861 adapter->stats.rx_bytes);
3862 seq_printf(seq, "rx stats: broadcasts : %8.8X\n",
3863 adapter->rcv_broadcasts);
3864 seq_printf(seq, "rx stats: multicasts : %8.8X\n",
3865 adapter->rcv_multicasts);
3866 seq_printf(seq, "rx stats: unicasts : %8.8X\n",
3867 adapter->rcv_unicasts);
3868 seq_printf(seq, "rx stats: errors : %8.8X\n",
e9eff9d6 3869 (u32) adapter->slic_stats.iface.rcv_errors);
4d6f6af8 3870 seq_printf(seq, "rx stats: Missed errors : %8.8X\n",
e9eff9d6 3871 (u32) adapter->slic_stats.iface.rcv_discards);
4d6f6af8 3872 seq_printf(seq, "rx stats: drops : %8.8X\n",
e9eff9d6 3873 (u32) adapter->rcv_drops);
4d6f6af8
GKH
3874 seq_printf(seq, "tx stats: packets : %8.8lX\n",
3875 adapter->stats.tx_packets);
3876 seq_printf(seq, "tx stats: bytes : %8.8lX\n",
3877 adapter->stats.tx_bytes);
3878 seq_printf(seq, "tx stats: errors : %8.8X\n",
e9eff9d6 3879 (u32) adapter->slic_stats.iface.xmt_errors);
4d6f6af8
GKH
3880 seq_printf(seq, "rx stats: multicasts : %8.8lX\n",
3881 adapter->stats.multicast);
3882 seq_printf(seq, "tx stats: collision errors : %8.8X\n",
e9eff9d6 3883 (u32) adapter->slic_stats.iface.xmit_collisions);
4d6f6af8
GKH
3884 seq_printf(seq, "perf: Max rcv frames/isr : %8.8X\n",
3885 adapter->max_isr_rcvs);
3886 seq_printf(seq, "perf: Rcv interrupt yields : %8.8X\n",
3887 adapter->rcv_interrupt_yields);
3888 seq_printf(seq, "perf: Max xmit complete/isr : %8.8X\n",
3889 adapter->max_isr_xmits);
3890 seq_printf(seq, "perf: error interrupts : %8.8X\n",
3891 adapter->error_interrupts);
3892 seq_printf(seq, "perf: error rmiss interrupts : %8.8X\n",
3893 adapter->error_rmiss_interrupts);
3894 seq_printf(seq, "perf: rcv interrupts : %8.8X\n",
3895 adapter->rcv_interrupts);
3896 seq_printf(seq, "perf: xmit interrupts : %8.8X\n",
3897 adapter->xmit_interrupts);
3898 seq_printf(seq, "perf: link event interrupts : %8.8X\n",
3899 adapter->linkevent_interrupts);
3900 seq_printf(seq, "perf: UPR interrupts : %8.8X\n",
3901 adapter->upr_interrupts);
3902 seq_printf(seq, "perf: interrupt count : %8.8X\n",
3903 adapter->num_isrs);
3904 seq_printf(seq, "perf: false interrupts : %8.8X\n",
3905 adapter->false_interrupts);
3906 seq_printf(seq, "perf: All register writes : %8.8X\n",
3907 adapter->all_reg_writes);
3908 seq_printf(seq, "perf: ICR register writes : %8.8X\n",
3909 adapter->icr_reg_writes);
3910 seq_printf(seq, "perf: ISR register writes : %8.8X\n",
3911 adapter->isr_reg_writes);
3912 seq_printf(seq, "ifevents: overflow 802 errors : %8.8X\n",
3913 adapter->if_events.oflow802);
3914 seq_printf(seq, "ifevents: transport overflow errors: %8.8X\n",
3915 adapter->if_events.Tprtoflow);
3916 seq_printf(seq, "ifevents: underflow errors : %8.8X\n",
3917 adapter->if_events.uflow802);
3918 seq_printf(seq, "ifevents: receive early : %8.8X\n",
3919 adapter->if_events.rcvearly);
3920 seq_printf(seq, "ifevents: buffer overflows : %8.8X\n",
3921 adapter->if_events.Bufov);
3922 seq_printf(seq, "ifevents: carrier errors : %8.8X\n",
3923 adapter->if_events.Carre);
3924 seq_printf(seq, "ifevents: Long : %8.8X\n",
3925 adapter->if_events.Longe);
3926 seq_printf(seq, "ifevents: invalid preambles : %8.8X\n",
3927 adapter->if_events.Invp);
3928 seq_printf(seq, "ifevents: CRC errors : %8.8X\n",
3929 adapter->if_events.Crc);
3930 seq_printf(seq, "ifevents: dribble nibbles : %8.8X\n",
3931 adapter->if_events.Drbl);
3932 seq_printf(seq, "ifevents: Code violations : %8.8X\n",
3933 adapter->if_events.Code);
3934 seq_printf(seq, "ifevents: TCP checksum errors : %8.8X\n",
3935 adapter->if_events.TpCsum);
3936 seq_printf(seq, "ifevents: TCP header short errors : %8.8X\n",
3937 adapter->if_events.TpHlen);
3938 seq_printf(seq, "ifevents: IP checksum errors : %8.8X\n",
3939 adapter->if_events.IpCsum);
3940 seq_printf(seq, "ifevents: IP frame incompletes : %8.8X\n",
3941 adapter->if_events.IpLen);
3942 seq_printf(seq, "ifevents: IP headers shorts : %8.8X\n",
3943 adapter->if_events.IpHlen);
3944
3945 return 0;
3946}
3947static int slic_debug_adapter_open(struct inode *inode, struct file *file)
3948{
3949 return single_open(file, slic_debug_adapter_show, inode->i_private);
3950}
3951
3952static int slic_debug_card_open(struct inode *inode, struct file *file)
3953{
3954 return single_open(file, slic_debug_card_show, inode->i_private);
3955}
3956
3957static const struct file_operations slic_debug_adapter_fops = {
3958 .owner = THIS_MODULE,
3959 .open = slic_debug_adapter_open,
3960 .read = seq_read,
3961 .llseek = seq_lseek,
3962 .release = single_release,
3963};
3964
3965static const struct file_operations slic_debug_card_fops = {
3966 .owner = THIS_MODULE,
3967 .open = slic_debug_card_open,
3968 .read = seq_read,
3969 .llseek = seq_lseek,
3970 .release = single_release,
3971};
3972
e9eff9d6 3973static void slic_debug_adapter_create(struct adapter *adapter)
4d6f6af8
GKH
3974{
3975 struct dentry *d;
3976 char name[7];
e9eff9d6 3977 struct sliccard *card = adapter->card;
4d6f6af8
GKH
3978
3979 if (!card->debugfs_dir)
3980 return;
3981
3982 sprintf(name, "port%d", adapter->port);
3983 d = debugfs_create_file(name, S_IRUGO,
3984 card->debugfs_dir, adapter,
3985 &slic_debug_adapter_fops);
3986 if (!d || IS_ERR(d))
3987 pr_info(PFX "%s: debugfs create failed\n", name);
3988 else
3989 adapter->debugfs_entry = d;
3990}
3991
e9eff9d6 3992static void slic_debug_adapter_destroy(struct adapter *adapter)
4d6f6af8
GKH
3993{
3994 if (adapter->debugfs_entry) {
3995 debugfs_remove(adapter->debugfs_entry);
3996 adapter->debugfs_entry = NULL;
3997 }
3998}
3999
e9eff9d6 4000static void slic_debug_card_create(struct sliccard *card)
4d6f6af8
GKH
4001{
4002 struct dentry *d;
4003 char name[IFNAMSIZ];
4004
4005 snprintf(name, sizeof(name), "slic%d", card->cardnum);
4006 d = debugfs_create_dir(name, slic_debugfs);
4007 if (!d || IS_ERR(d))
4008 pr_info(PFX "%s: debugfs create dir failed\n",
4009 name);
4010 else {
4011 card->debugfs_dir = d;
4012 d = debugfs_create_file("cardinfo", S_IRUGO,
4013 slic_debugfs, card,
4014 &slic_debug_card_fops);
4015 if (!d || IS_ERR(d))
4016 pr_info(PFX "%s: debugfs create failed\n",
4017 name);
4018 else
4019 card->debugfs_cardinfo = d;
4020 }
4021}
4022
e9eff9d6 4023static void slic_debug_card_destroy(struct sliccard *card)
4d6f6af8
GKH
4024{
4025 int i;
4026
4027 for (i = 0; i < card->card_size; i++) {
e9eff9d6 4028 struct adapter *adapter;
4d6f6af8
GKH
4029
4030 adapter = card->adapter[i];
4031 if (adapter)
4032 slic_debug_adapter_destroy(adapter);
4033 }
4034 if (card->debugfs_cardinfo) {
4035 debugfs_remove(card->debugfs_cardinfo);
4036 card->debugfs_cardinfo = NULL;
4037 }
4038 if (card->debugfs_dir) {
4039 debugfs_remove(card->debugfs_dir);
4040 card->debugfs_dir = NULL;
4041 }
4042}
4043
4044static void slic_debug_init(void)
4045{
4046 struct dentry *ent;
4047
4048 ent = debugfs_create_dir("slic", NULL);
4049 if (!ent || IS_ERR(ent)) {
4050 pr_info(PFX "debugfs create directory failed\n");
4051 return;
4052 }
4053
4054 slic_debugfs = ent;
4055}
4056
4057static void slic_debug_cleanup(void)
4058{
4059 if (slic_debugfs) {
4060 debugfs_remove(slic_debugfs);
4061 slic_debugfs = NULL;
4062 }
4063}
4064
4d6f6af8
GKH
4065/******************************************************************************/
4066/**************** MODULE INITIATION / TERMINATION FUNCTIONS ***************/
4067/******************************************************************************/
4068
4069static struct pci_driver slic_driver = {
4070 .name = DRV_NAME,
4071 .id_table = slic_pci_tbl,
4072 .probe = slic_entry_probe,
4073 .remove = slic_entry_remove,
4d6f6af8
GKH
4074};
4075
4076static int __init slic_module_init(void)
4077{
4d6f6af8
GKH
4078 slic_init_driver();
4079
4080 if (debug >= 0 && slic_debug != debug)
4081 printk(SLICLEVEL "slicoss: debug level is %d.\n", debug);
4082 if (debug >= 0)
4083 slic_debug = debug;
4084
e8bc9b7a 4085 return pci_register_driver(&slic_driver);
4d6f6af8
GKH
4086}
4087
4088static void __exit slic_module_cleanup(void)
4089{
4d6f6af8
GKH
4090 pci_unregister_driver(&slic_driver);
4091 slic_debug_cleanup();
4d6f6af8
GKH
4092}
4093
4094module_init(slic_module_init);
4095module_exit(slic_module_cleanup);