1/******************************************************************************/
2/*                                                                            */
3/* Broadcom BCM5700 Linux Network Driver, Copyright (c) 2000 - 2004 Broadcom  */
4/* Corporation.                                                               */
5/* All rights reserved.                                                       */
6/*                                                                            */
7/* This program is free software; you can redistribute it and/or modify       */
8/* it under the terms of the GNU General Public License as published by       */
9/* the Free Software Foundation, located in the file LICENSE.                 */
10/*                                                                            */
11/******************************************************************************/
12
13#ifndef MM_H
14#define MM_H
15
16#include <linux/config.h>
17
18#if defined(CONFIG_SMP) && !defined(__SMP__)
19#define __SMP__
20#endif
21
22#if defined(CONFIG_MODVERSIONS) && defined(MODULE) && !defined(MODVERSIONS)
23#ifndef BCM_SMALL_DRV
24#define MODVERSIONS
25#endif
26#endif
27
28#ifndef B57UM
29#define __NO_VERSION__
30#endif
31#include <linux/version.h>
32
33#ifdef MODULE
34
35#if defined(MODVERSIONS) && (LINUX_VERSION_CODE < 0x020500)
36#ifndef BCM_SMALL_DRV
37#include <linux/modversions.h>
38#endif
39#endif
40
41#if (LINUX_VERSION_CODE < 0x020605)
42#include <linux/module.h>
43#else
44#include <linux/moduleparam.h>
45#endif
46
47#else
48
49#define MOD_INC_USE_COUNT
50#define MOD_DEC_USE_COUNT
51#define SET_MODULE_OWNER(dev)
52#define MODULE_DEVICE_TABLE(pci, pci_tbl)
53#endif
54
55
56#include <linux/kernel.h>
57#include <linux/sched.h>
58#include <linux/string.h>
59#include <linux/timer.h>
60#include <linux/errno.h>
61#include <linux/ioport.h>
62#include <linux/slab.h>
63#include <linux/interrupt.h>
64#include <linux/pci.h>
65#include <linux/init.h>
66#include <linux/netdevice.h>
67#include <linux/etherdevice.h>
68#include <linux/skbuff.h>
69#include <asm/processor.h>		/* Processor type for cache alignment. */
70#include <asm/bitops.h>
71#include <asm/io.h>
72#include <asm/unaligned.h>
73#include <linux/delay.h>
74#include <asm/byteorder.h>
75#include <linux/time.h>
76#include <asm/uaccess.h>
77#if (LINUX_VERSION_CODE >= 0x020400)
78#if (LINUX_VERSION_CODE < 0x020500)
79#include <linux/wrapper.h>
80#endif
81#include <linux/ethtool.h>
82#endif
83#ifdef CONFIG_PROC_FS
84#include <linux/smp_lock.h>
85#include <linux/proc_fs.h>
86#define BCM_PROC_FS 1
87#endif
88#ifdef NETIF_F_HW_VLAN_TX
89#include <linux/if_vlan.h>
90#define BCM_VLAN 1
91#endif
92#ifdef NETIF_F_TSO
93#define BCM_TSO 1
94#define INCLUDE_TCP_SEG_SUPPORT 1
95#include <net/ip.h>
96#include <net/tcp.h>
97#include <net/checksum.h>
98#endif
99
100#ifndef LINUX_KERNEL_VERSION
101#define LINUX_KERNEL_VERSION	0
102#endif
103
104#ifndef MAX_SKB_FRAGS
105#define MAX_SKB_FRAGS	0
106#endif
107
108#if (LINUX_VERSION_CODE >= 0x020400)
109#ifndef ETHTOOL_GEEPROM
110
111#define ETHTOOL_GEEPROM		0x0000000b /* Get EEPROM data */
112#define ETHTOOL_SEEPROM		0x0000000c /* Set EEPROM data */
113
114/* for passing EEPROM chunks */
115struct ethtool_eeprom {
116	u32	cmd;
117	u32	magic;
118	u32	offset; /* in bytes */
119	u32	len; /* in bytes */
120	u8	data[0];
121};
122#define BCM_EEDUMP_LEN(info_p, size) *((u32 *) &((info_p)->reserved1[24]))=size
123
124#else
125
126#define BCM_EEDUMP_LEN(info_p, size) (info_p)->eedump_len=size
127
128#endif
129#endif
130
131#define BCM_INT_COAL 1
132#define BCM_NIC_SEND_BD 1
133#define BCM_ASF 1
134#define BCM_WOL 1
135#define BCM_TASKLET 1
136
137#if HAVE_NETIF_RECEIVE_SKB
138#define BCM_NAPI_RXPOLL 1
139#undef BCM_TASKLET
140#endif
141
142#if defined(CONFIG_PPC64)
143#define BCM_DISCONNECT_AT_CACHELINE 1
144#endif
145
146#ifdef BCM_SMALL_DRV
147#undef BCM_PROC_FS
148#undef ETHTOOL_GEEPROM
149#undef ETHTOOL_SEEPROM
150#undef ETHTOOL_GREGS
151#undef ETHTOOL_GPAUSEPARAM
152#undef ETHTOOL_GRXCSUM
153#undef ETHTOOL_TEST
154#undef BCM_INT_COAL
155#undef BCM_NIC_SEND_BD
156#undef BCM_WOL
157#undef NICE_SUPPORT
158#undef BCM_TASKLET
159#undef BCM_TSO
160#endif
161
162#ifdef __BIG_ENDIAN
163#define BIG_ENDIAN_HOST 1
164#endif
165
166#define MM_SWAP_LE32(x) cpu_to_le32(x)
167#define MM_SWAP_BE32(x) cpu_to_be32(x)
168
169#if (LINUX_VERSION_CODE < 0x020327)
170#define __raw_readl readl
171#define __raw_writel writel
172#endif
173
174#define MM_MEMWRITEL(ptr, val) __raw_writel(val, ptr)
175#define MM_MEMREADL(ptr) __raw_readl(ptr)
176
177typedef atomic_t MM_ATOMIC_T;
178
179#define MM_ATOMIC_SET(ptr, val) atomic_set(ptr, val)
180#define MM_ATOMIC_READ(ptr) atomic_read(ptr)
181#define MM_ATOMIC_INC(ptr) atomic_inc(ptr)
182#define MM_ATOMIC_ADD(ptr, val) atomic_add(val, ptr)
183#define MM_ATOMIC_DEC(ptr) atomic_dec(ptr)
184#define MM_ATOMIC_SUB(ptr, val) atomic_sub(val, ptr)
185
186
187#ifndef mmiowb
188#define mmiowb()
189#endif
190
191
192#define MM_MB() mb()
193#define MM_WMB() wmb()
194#define MM_RMB() rmb()
195#define MM_MMIOWB() mmiowb()
196
197#include "lm.h"
198#include "queue.h"
199#include "tigon3.h"
200
201#if DBG
202#define STATIC
203#else
204#define STATIC static
205#endif
206
207extern int MM_Packet_Desc_Size;
208
209#define MM_PACKET_DESC_SIZE MM_Packet_Desc_Size
210
211DECLARE_QUEUE_TYPE(UM_RX_PACKET_Q, MAX_RX_PACKET_DESC_COUNT+1);
212
213#define MAX_MEM 16
214#define MAX_MEM2 4
215
216#if (LINUX_VERSION_CODE < 0x020211)
217typedef u32 dma_addr_t;
218#endif
219
220#if (LINUX_VERSION_CODE < 0x02032a)
221#define pci_map_single(dev, address, size, dir) virt_to_bus(address)
222#define pci_unmap_single(dev, dma_addr, size, dir)
223#endif
224
225#if MAX_SKB_FRAGS
226#if (LINUX_VERSION_CODE >= 0x02040d)
227
228typedef dma_addr_t dmaaddr_high_t;
229
230#else
231
232#if defined(CONFIG_HIGHMEM) && defined(CONFIG_X86) && !defined(CONFIG_X86_64)
233
234#if defined(CONFIG_HIGHMEM64G)
235typedef unsigned long long dmaaddr_high_t;
236#else
237typedef dma_addr_t dmaaddr_high_t;
238#endif
239
240#ifndef pci_map_page
241#define pci_map_page bcm_pci_map_page
242#endif
243
244static inline dmaaddr_high_t
245bcm_pci_map_page(struct pci_dev *dev, struct page *page,
246		    int offset, size_t size, int dir)
247{
248	dmaaddr_high_t phys;
249
250	phys = (page-mem_map) *	(dmaaddr_high_t) PAGE_SIZE + offset;
251
252	return phys;
253}
254
255#ifndef pci_unmap_page
256#define pci_unmap_page(dev, map, size, dir)
257#endif
258
259#else /* #if defined(CONFIG_HIGHMEM) && defined(CONFIG_X86) && ! defined(CONFIG_X86_64)*/
260
261typedef dma_addr_t dmaaddr_high_t;
262
263/* Warning - This may not work for all architectures if HIGHMEM is defined */
264
265#ifndef pci_map_page
266#define pci_map_page(dev, page, offset, size, dir) \
267	pci_map_single(dev, page_address(page) + (offset), size, dir)
268#endif
269#ifndef pci_unmap_page
270#define pci_unmap_page(dev, map, size, dir) \
271	pci_unmap_single(dev, map, size, dir)
272#endif
273
274#endif /* #if defined(CONFIG_HIGHMEM) && defined(CONFIG_X86) && ! defined(CONFIG_X86_64)*/
275
276#endif /* #if (LINUX_VERSION_CODE >= 0x02040d)*/
277#endif /* #if MAX_SKB_FRAGS*/
278
279#if defined(CONFIG_X86) && !defined(CONFIG_X86_64)
280#define NO_PCI_UNMAP 1
281#endif
282
283#if (LINUX_VERSION_CODE < 0x020412)
284#if !defined(NO_PCI_UNMAP)
285#define DECLARE_PCI_UNMAP_ADDR(ADDR_NAME) dma_addr_t ADDR_NAME;
286#define DECLARE_PCI_UNMAP_LEN(LEN_NAME) __u32 LEN_NAME;
287
288#define pci_unmap_addr(PTR, ADDR_NAME)	\
289	((PTR)->ADDR_NAME)
290
291#define pci_unmap_len(PTR, LEN_NAME)	\
292	((PTR)->LEN_NAME)
293
294#define pci_unmap_addr_set(PTR, ADDR_NAME, VAL)	\
295	(((PTR)->ADDR_NAME) = (VAL))
296
297#define pci_unmap_len_set(PTR, LEN_NAME, VAL)	\
298	(((PTR)->LEN_NAME) = (VAL))
299#else
300#define DECLARE_PCI_UNMAP_ADDR(ADDR_NAME)
301#define DECLARE_PCI_UNMAP_LEN(ADDR_NAME)
302
303#define pci_unmap_addr(PTR, ADDR_NAME)	0
304#define pci_unmap_len(PTR, LEN_NAME)	0
305#define pci_unmap_addr_set(PTR, ADDR_NAME, VAL) do { } while (0)
306#define pci_unmap_len_set(PTR, LEN_NAME, VAL) do { } while (0)
307#endif
308#endif
309
310#if (LINUX_VERSION_CODE < 0x02030e)
311#define net_device device
312#define netif_carrier_on(dev)
313#define netif_carrier_off(dev)
314#endif
315
316#if (LINUX_VERSION_CODE < 0x02032b)
317#define tasklet_struct			tq_struct
318#endif
319
320typedef struct _UM_DEVICE_BLOCK {
321	LM_DEVICE_BLOCK lm_dev;
322	struct net_device *dev;
323	struct pci_dev *pdev;
324	struct net_device *next_module;
325	char *name;
326#ifdef BCM_PROC_FS
327	struct proc_dir_entry *pfs_entry;
328	char pfs_name[32];
329#endif
330	void *mem_list[MAX_MEM];
331	dma_addr_t dma_list[MAX_MEM];
332	int mem_size_list[MAX_MEM];
333	int mem_list_num;
334
335#ifdef NICE_SUPPORT
336	void *mem_list2[MAX_MEM2];		/* for diagnostics ioctl */
337	dma_addr_t dma_list2[MAX_MEM2];
338	__u64 cpu_pa_list2[MAX_MEM2];
339	int mem_size_list2[MAX_MEM2];
340#endif
341	int index;
342	int opened;
343	int suspended;
344	int using_dac;		/* dual address cycle */
345	int delayed_link_ind; /* Delay link status during initial load */
346	int adapter_just_inited; /* the first few seconds after init. */
347	int timer_interval;
348	int statstimer_interval;
349	int adaptive_expiry;
350	int crc_counter_expiry;
351	int poll_tbi_interval;
352	int poll_tbi_expiry;
353	int asf_heartbeat;
354	int tx_full;
355	int tx_queued;
356	int line_speed;		/* in Mbps, 0 if link is down */
357	UM_RX_PACKET_Q rx_out_of_buf_q;
358	int rx_out_of_buf;
359	int rx_buf_repl_thresh;
360	int rx_buf_repl_panic_thresh;
361	int rx_buf_repl_isr_limit;
362	int rx_buf_align;
363	struct timer_list timer;
364	struct timer_list statstimer;
365	int do_global_lock;
366	spinlock_t global_lock;
367	spinlock_t undi_lock;
368	spinlock_t phy_lock;
369	unsigned long undi_flags;
370	volatile unsigned long interrupt;
371	atomic_t intr_sem;
372	int tasklet_pending;
373	volatile unsigned long tasklet_busy;
374	struct tasklet_struct tasklet;
375	struct net_device_stats stats;
376#ifdef NICE_SUPPORT
377	void (*nice_rx)( struct sk_buff*, void* );
378	void* nice_ctx;
379#endif /* NICE_SUPPORT */
380	int intr_test;
381	int intr_test_result;
382#ifdef NETIF_F_HW_VLAN_TX
383	struct vlan_group *vlgrp;
384#endif
385	int vlan_tag_mode;	/* Setting to allow ASF to work properly with */
386				/* VLANs                                      */
387	#define VLAN_TAG_MODE_AUTO_STRIP              0
388	#define VLAN_TAG_MODE_NORMAL_STRIP            1
389	#define VLAN_TAG_MODE_FORCED_STRIP            2
390
391	/* Auto mode - VLAN TAGs are always stripped if ASF is enabled,   */
392	/*             If ASF is not enabled, it will be in normal mode.  */
393	/* Normal mode - VLAN TAGs are stripped when VLANs are registered */
394	/* Forced mode - VLAN TAGs are always stripped.                   */
395
396	int adaptive_coalesce;
397	uint rx_last_cnt;
398	uint tx_last_cnt;
399	uint rx_curr_coalesce_frames;
400	uint rx_curr_coalesce_frames_intr;
401	uint rx_curr_coalesce_ticks;
402	uint tx_curr_coalesce_frames;
403#if TIGON3_DEBUG
404	unsigned long tx_zc_count;
405	unsigned long tx_chksum_count;
406	unsigned long tx_himem_count;
407	unsigned long rx_good_chksum_count;
408#endif
409	unsigned long rx_bad_chksum_count;
410#ifdef BCM_TSO
411	unsigned long tso_pkt_count;
412#endif
413	unsigned long rx_misc_errors;
414	uint64_t phy_crc_count;
415	unsigned int spurious_int;
416
417	void		*sbh;
418	unsigned long	boardflags;
419	void		*robo;
420} UM_DEVICE_BLOCK, *PUM_DEVICE_BLOCK;
421
422typedef struct _UM_PACKET {
423	LM_PACKET lm_packet;
424	struct sk_buff *skbuff;
425#if MAX_SKB_FRAGS
426	DECLARE_PCI_UNMAP_ADDR(map[MAX_SKB_FRAGS + 1])
427	DECLARE_PCI_UNMAP_LEN(map_len[MAX_SKB_FRAGS + 1])
428#else
429	DECLARE_PCI_UNMAP_ADDR(map[1])
430	DECLARE_PCI_UNMAP_LEN(map_len[1])
431#endif
432} UM_PACKET, *PUM_PACKET;
433
434static inline void MM_SetAddr(LM_PHYSICAL_ADDRESS *paddr, dma_addr_t addr)
435{
436#if BITS_PER_LONG == 64
437	paddr->High = ((unsigned long) addr) >> 32;
438	paddr->Low = ((unsigned long) addr) & 0xffffffff;
439#else
440	paddr->High = 0;
441	paddr->Low = (unsigned long) addr;
442#endif
443}
444
445static inline void MM_SetT3Addr(T3_64BIT_HOST_ADDR *paddr, dma_addr_t addr)
446{
447#if BITS_PER_LONG == 64
448	paddr->High = ((unsigned long) addr) >> 32;
449	paddr->Low = ((unsigned long) addr) & 0xffffffff;
450#else
451	paddr->High = 0;
452	paddr->Low = (unsigned long) addr;
453#endif
454}
455
456#if MAX_SKB_FRAGS
457static inline void MM_SetT3AddrHigh(T3_64BIT_HOST_ADDR *paddr,
458	dmaaddr_high_t addr)
459{
460#if defined(CONFIG_HIGHMEM64G) && defined(CONFIG_X86) && !defined(CONFIG_X86_64)
461	paddr->High = (unsigned long) (addr >> 32);
462	paddr->Low = (unsigned long) (addr & 0xffffffff);
463#else
464	MM_SetT3Addr(paddr, (dma_addr_t) addr);
465#endif
466}
467#endif
468
469static inline void MM_MapRxDma(PLM_DEVICE_BLOCK pDevice,
470	struct _LM_PACKET *pPacket,
471	T3_64BIT_HOST_ADDR *paddr)
472{
473	dma_addr_t map;
474	struct sk_buff *skb = ((struct _UM_PACKET *) pPacket)->skbuff;
475
476	map = pci_map_single(((struct _UM_DEVICE_BLOCK *)pDevice)->pdev,
477			skb->tail,
478			pPacket->u.Rx.RxBufferSize,
479			PCI_DMA_FROMDEVICE);
480	pci_unmap_addr_set(((struct _UM_PACKET *) pPacket), map[0], map);
481	MM_SetT3Addr(paddr, map);
482}
483
484static inline void MM_MapTxDma(PLM_DEVICE_BLOCK pDevice,
485	struct _LM_PACKET *pPacket,
486	T3_64BIT_HOST_ADDR *paddr,
487	LM_UINT32 *len,
488	int frag)
489{
490	dma_addr_t map;
491	struct sk_buff *skb = ((struct _UM_PACKET *) pPacket)->skbuff;
492	unsigned int length;
493
494	if (frag == 0) {
495#if MAX_SKB_FRAGS
496		if (skb_shinfo(skb)->nr_frags)
497			length = skb->len - skb->data_len;
498		else
499#endif
500			length = skb->len;
501		map = pci_map_single(((struct _UM_DEVICE_BLOCK *)pDevice)->pdev,
502			skb->data, length, PCI_DMA_TODEVICE);
503		MM_SetT3Addr(paddr, map);
504		pci_unmap_addr_set(((struct _UM_PACKET *)pPacket), map[0], map);
505		pci_unmap_len_set(((struct _UM_PACKET *) pPacket), map_len[0],
506			length);
507		*len = length;
508	}
509#if MAX_SKB_FRAGS
510	else {
511		skb_frag_t *sk_frag;
512		dmaaddr_high_t hi_map;
513
514		sk_frag = &skb_shinfo(skb)->frags[frag - 1];
515
516		hi_map = pci_map_page(
517				((struct _UM_DEVICE_BLOCK *)pDevice)->pdev,
518				sk_frag->page,
519				sk_frag->page_offset,
520				sk_frag->size, PCI_DMA_TODEVICE);
521
522		MM_SetT3AddrHigh(paddr, hi_map);
523		pci_unmap_addr_set(((struct _UM_PACKET *) pPacket), map[frag],
524			hi_map);
525		pci_unmap_len_set(((struct _UM_PACKET *) pPacket),
526			map_len[frag], sk_frag->size);
527		*len = sk_frag->size;
528	}
529#endif
530}
531
532#define BCM5700_PHY_LOCK(pUmDevice, flags) {				\
533	spinlock_t *lock;						\
534	if ((pUmDevice)->do_global_lock) {				\
535		lock = &(pUmDevice)->global_lock;			\
536	}								\
537	else {								\
538		lock = &(pUmDevice)->phy_lock;				\
539	}								\
540	spin_lock_irqsave(lock, flags);					\
541}
542
543#define BCM5700_PHY_UNLOCK(pUmDevice, flags) {				\
544	spinlock_t *lock;						\
545	if ((pUmDevice)->do_global_lock) {				\
546		lock = &(pUmDevice)->global_lock;			\
547	}								\
548	else {								\
549		lock = &(pUmDevice)->phy_lock;				\
550	}								\
551	spin_unlock_irqrestore(lock, flags);				\
552}
553
554
555#define MM_ACQUIRE_UNDI_LOCK(_pDevice) \
556	if (!(((PUM_DEVICE_BLOCK)(_pDevice))->do_global_lock)) {	\
557		unsigned long flags;					\
558		spin_lock_irqsave(&((PUM_DEVICE_BLOCK)(_pDevice))->undi_lock, flags);	\
559		((PUM_DEVICE_BLOCK)(_pDevice))->undi_flags = flags; \
560	}
561
562#define MM_RELEASE_UNDI_LOCK(_pDevice) \
563	if (!(((PUM_DEVICE_BLOCK)(_pDevice))->do_global_lock)) {	\
564		unsigned long flags = ((PUM_DEVICE_BLOCK) (_pDevice))->undi_flags; \
565		spin_unlock_irqrestore(&((PUM_DEVICE_BLOCK)(_pDevice))->undi_lock, flags); \
566	}
567
568#define MM_ACQUIRE_PHY_LOCK_IN_IRQ(_pDevice) \
569	if (!(((PUM_DEVICE_BLOCK)(_pDevice))->do_global_lock)) {	\
570		spin_lock(&((PUM_DEVICE_BLOCK)(_pDevice))->phy_lock);	\
571	}
572
573#define MM_RELEASE_PHY_LOCK_IN_IRQ(_pDevice) \
574	if (!(((PUM_DEVICE_BLOCK)(_pDevice))->do_global_lock)) {	\
575		spin_unlock(&((PUM_DEVICE_BLOCK)(_pDevice))->phy_lock); \
576	}
577
578#define MM_UINT_PTR(_ptr)   ((unsigned long) (_ptr))
579
580#define MM_GETSTATS64(_Ctr) \
581	(uint64_t) (_Ctr).Low + ((uint64_t) (_Ctr).High << 32)
582
583#define MM_GETSTATS32(_Ctr) \
584	(uint32_t) (_Ctr).Low
585
586#if BITS_PER_LONG == 64
587#define MM_GETSTATS(_Ctr) (unsigned long) MM_GETSTATS64(_Ctr)
588#else
589#define MM_GETSTATS(_Ctr) (unsigned long) MM_GETSTATS32(_Ctr)
590#endif
591
592#if (LINUX_VERSION_CODE >= 0x020600)
593#define mm_copy_to_user( to, from, size ) \
594	(in_atomic() ? (memcpy((to),(from),(size)), 0) : copy_to_user((to),(from),(size)))
595#define mm_copy_from_user( to, from, size ) \
596	(in_atomic() ? (memcpy((to),(from),(size)), 0) : copy_from_user((to),(from),(size)))
597#else
598#define mm_copy_to_user( to, from, size )	\
599		copy_to_user((to),(from),(size) )
600#define mm_copy_from_user( to, from, size )	\
601		copy_from_user((to),(from),(size))
602#endif
603
604#ifndef printf
605#define printf(fmt, args...) printk(KERN_WARNING fmt, ##args)
606#endif
607
608#define DbgPrint(fmt, arg...) printk(KERN_DEBUG fmt, ##arg)
609#if defined(CONFIG_X86)
610#define DbgBreakPoint() __asm__("int $129")
611#else
612#define DbgBreakPoint()
613#endif
614#define MM_Wait(time) udelay(time)
615
616#endif
617