• Home
  • History
  • Annotate
  • Line#
  • Navigate
  • Raw
  • Download
  • only in /netgear-R7000-V1.0.7.12_1.2.5/components/opensource/linux/linux-2.6.36/drivers/net/tulip/
1/*
2	drivers/net/tulip/eeprom.c
3
4	Copyright 2000,2001  The Linux Kernel Team
5	Written/copyright 1994-2001 by Donald Becker.
6
7	This software may be used and distributed according to the terms
8	of the GNU General Public License, incorporated herein by reference.
9
10	Please refer to Documentation/DocBook/tulip-user.{pdf,ps,html}
11	for more information on this driver.
12	Please submit bug reports to http://bugzilla.kernel.org/.
13*/
14
15#include <linux/pci.h>
16#include <linux/slab.h>
17#include "tulip.h"
18#include <linux/init.h>
19#include <asm/unaligned.h>
20
21
22
23/* Serial EEPROM section. */
24/* The main routine to parse the very complicated SROM structure.
25   Search www.digital.com for "21X4 SROM" to get details.
26   This code is very complex, and will require changes to support
27   additional cards, so I'll be verbose about what is going on.
28   */
29
30/* Known cards that have old-style EEPROMs. */
31static struct eeprom_fixup eeprom_fixups[] __devinitdata = {
32  {"Asante", 0, 0, 0x94, {0x1e00, 0x0000, 0x0800, 0x0100, 0x018c,
33			  0x0000, 0x0000, 0xe078, 0x0001, 0x0050, 0x0018 }},
34  {"SMC9332DST", 0, 0, 0xC0, { 0x1e00, 0x0000, 0x0800, 0x041f,
35			   0x0000, 0x009E, /* 10baseT */
36			   0x0004, 0x009E, /* 10baseT-FD */
37			   0x0903, 0x006D, /* 100baseTx */
38			   0x0905, 0x006D, /* 100baseTx-FD */ }},
39  {"Cogent EM100", 0, 0, 0x92, { 0x1e00, 0x0000, 0x0800, 0x063f,
40				 0x0107, 0x8021, /* 100baseFx */
41				 0x0108, 0x8021, /* 100baseFx-FD */
42				 0x0100, 0x009E, /* 10baseT */
43				 0x0104, 0x009E, /* 10baseT-FD */
44				 0x0103, 0x006D, /* 100baseTx */
45				 0x0105, 0x006D, /* 100baseTx-FD */ }},
46  {"Maxtech NX-110", 0, 0, 0xE8, { 0x1e00, 0x0000, 0x0800, 0x0513,
47				   0x1001, 0x009E, /* 10base2, CSR12 0x10*/
48				   0x0000, 0x009E, /* 10baseT */
49				   0x0004, 0x009E, /* 10baseT-FD */
50				   0x0303, 0x006D, /* 100baseTx, CSR12 0x03 */
51				   0x0305, 0x006D, /* 100baseTx-FD CSR12 0x03 */}},
52  {"Accton EN1207", 0, 0, 0xE8, { 0x1e00, 0x0000, 0x0800, 0x051F,
53				  0x1B01, 0x0000, /* 10base2,   CSR12 0x1B */
54				  0x0B00, 0x009E, /* 10baseT,   CSR12 0x0B */
55				  0x0B04, 0x009E, /* 10baseT-FD,CSR12 0x0B */
56				  0x1B03, 0x006D, /* 100baseTx, CSR12 0x1B */
57				  0x1B05, 0x006D, /* 100baseTx-FD CSR12 0x1B */
58   }},
59  {"NetWinder", 0x00, 0x10, 0x57,
60	/* Default media = MII
61	 * MII block, reset sequence (3) = 0x0821 0x0000 0x0001, capabilities 0x01e1
62	 */
63	{ 0x1e00, 0x0000, 0x000b, 0x8f01, 0x0103, 0x0300, 0x0821, 0x000, 0x0001, 0x0000, 0x01e1 }
64  },
65  {"Cobalt Microserver", 0, 0x10, 0xE0, {0x1e00, /* 0 == controller #, 1e == offset	*/
66					 0x0000, /* 0 == high offset, 0 == gap		*/
67					 0x0800, /* Default Autoselect			*/
68					 0x8001, /* 1 leaf, extended type, bogus len	*/
69					 0x0003, /* Type 3 (MII), PHY #0		*/
70					 0x0400, /* 0 init instr, 4 reset instr		*/
71					 0x0801, /* Set control mode, GP0 output	*/
72					 0x0000, /* Drive GP0 Low (RST is active low)	*/
73					 0x0800, /* control mode, GP0 input (undriven)	*/
74					 0x0000, /* clear control mode			*/
75					 0x7800, /* 100TX FDX + HDX, 10bT FDX + HDX	*/
76					 0x01e0, /* Advertise all above			*/
77					 0x5000, /* FDX all above			*/
78					 0x1800, /* Set fast TTM in 100bt modes		*/
79					 0x0000, /* PHY cannot be unplugged		*/
80  }},
81  {NULL}};
82
83
84static const char *block_name[] __devinitdata = {
85	"21140 non-MII",
86	"21140 MII PHY",
87	"21142 Serial PHY",
88	"21142 MII PHY",
89	"21143 SYM PHY",
90	"21143 reset method"
91};
92
93
94/**
95 * tulip_build_fake_mediatable - Build a fake mediatable entry.
96 * @tp: Ptr to the tulip private data.
97 *
98 * Some cards like the 3x5 HSC cards (J3514A) do not have a standard
99 * srom and can not be handled under the fixup routine.  These cards
100 * still need a valid mediatable entry for correct csr12 setup and
101 * mii handling.
102 *
103 * Since this is currently a parisc-linux specific function, the
104 * #ifdef __hppa__ should completely optimize this function away for
105 * non-parisc hardware.
106 */
107static void __devinit tulip_build_fake_mediatable(struct tulip_private *tp)
108{
109#ifdef CONFIG_GSC
110	if (tp->flags & NEEDS_FAKE_MEDIA_TABLE) {
111		static unsigned char leafdata[] =
112			{ 0x01,       /* phy number */
113			  0x02,       /* gpr setup sequence length */
114			  0x02, 0x00, /* gpr setup sequence */
115			  0x02,       /* phy reset sequence length */
116			  0x01, 0x00, /* phy reset sequence */
117			  0x00, 0x78, /* media capabilities */
118			  0x00, 0xe0, /* nway advertisment */
119			  0x00, 0x05, /* fdx bit map */
120			  0x00, 0x06  /* ttm bit map */
121			};
122
123		tp->mtable = kmalloc(sizeof(struct mediatable) +
124				     sizeof(struct medialeaf), GFP_KERNEL);
125
126		if (tp->mtable == NULL)
127			return; /* Horrible, impossible failure. */
128
129		tp->mtable->defaultmedia = 0x800;
130		tp->mtable->leafcount = 1;
131		tp->mtable->csr12dir = 0x3f; /* inputs on bit7 for hsc-pci, bit6 for pci-fx */
132		tp->mtable->has_nonmii = 0;
133		tp->mtable->has_reset = 0;
134		tp->mtable->has_mii = 1;
135		tp->mtable->csr15dir = tp->mtable->csr15val = 0;
136		tp->mtable->mleaf[0].type = 1;
137		tp->mtable->mleaf[0].media = 11;
138		tp->mtable->mleaf[0].leafdata = &leafdata[0];
139		tp->flags |= HAS_PHY_IRQ;
140		tp->csr12_shadow = -1;
141	}
142#endif
143}
144
145void __devinit tulip_parse_eeprom(struct net_device *dev)
146{
147	/*
148	  dev is not registered at this point, so logging messages can't
149	  use dev_<level> or netdev_<level> but dev->name is good via a
150	  hack in the caller
151	*/
152
153	/* The last media info list parsed, for multiport boards.  */
154	static struct mediatable *last_mediatable;
155	static unsigned char *last_ee_data;
156	static int controller_index;
157	struct tulip_private *tp = netdev_priv(dev);
158	unsigned char *ee_data = tp->eeprom;
159	int i;
160
161	tp->mtable = NULL;
162	/* Detect an old-style (SA only) EEPROM layout:
163	   memcmp(eedata, eedata+16, 8). */
164	for (i = 0; i < 8; i ++)
165		if (ee_data[i] != ee_data[16+i])
166			break;
167	if (i >= 8) {
168		if (ee_data[0] == 0xff) {
169			if (last_mediatable) {
170				controller_index++;
171				pr_info("%s: Controller %d of multiport board\n",
172					dev->name, controller_index);
173				tp->mtable = last_mediatable;
174				ee_data = last_ee_data;
175				goto subsequent_board;
176			} else
177				pr_info("%s: Missing EEPROM, this interface may not work correctly!\n",
178					dev->name);
179			return;
180		}
181	  /* Do a fix-up based on the vendor half of the station address prefix. */
182	  for (i = 0; eeprom_fixups[i].name; i++) {
183		  if (dev->dev_addr[0] == eeprom_fixups[i].addr0 &&
184		      dev->dev_addr[1] == eeprom_fixups[i].addr1 &&
185		      dev->dev_addr[2] == eeprom_fixups[i].addr2) {
186		  if (dev->dev_addr[2] == 0xE8 && ee_data[0x1a] == 0x55)
187			  i++;			/* An Accton EN1207, not an outlaw Maxtech. */
188		  memcpy(ee_data + 26, eeprom_fixups[i].newtable,
189				 sizeof(eeprom_fixups[i].newtable));
190		  pr_info("%s: Old format EEPROM on '%s' board.  Using substitute media control info\n",
191			  dev->name, eeprom_fixups[i].name);
192		  break;
193		}
194	  }
195	  if (eeprom_fixups[i].name == NULL) { /* No fixup found. */
196		  pr_info("%s: Old style EEPROM with no media selection information\n",
197			  dev->name);
198		return;
199	  }
200	}
201
202	controller_index = 0;
203	if (ee_data[19] > 1) {		/* Multiport board. */
204		last_ee_data = ee_data;
205	}
206subsequent_board:
207
208	if (ee_data[27] == 0) {		/* No valid media table. */
209		tulip_build_fake_mediatable(tp);
210	} else {
211		unsigned char *p = (void *)ee_data + ee_data[27];
212		unsigned char csr12dir = 0;
213		int count, new_advertise = 0;
214		struct mediatable *mtable;
215		u16 media = get_u16(p);
216
217		p += 2;
218		if (tp->flags & CSR12_IN_SROM)
219			csr12dir = *p++;
220		count = *p++;
221
222	        /* there is no phy information, don't even try to build mtable */
223	        if (count == 0) {
224			if (tulip_debug > 0)
225				pr_warning("%s: no phy info, aborting mtable build\n",
226					   dev->name);
227		        return;
228		}
229
230		mtable = kmalloc(sizeof(struct mediatable) +
231				 count * sizeof(struct medialeaf),
232				 GFP_KERNEL);
233		if (mtable == NULL)
234			return;				/* Horrible, impossible failure. */
235		last_mediatable = tp->mtable = mtable;
236		mtable->defaultmedia = media;
237		mtable->leafcount = count;
238		mtable->csr12dir = csr12dir;
239		mtable->has_nonmii = mtable->has_mii = mtable->has_reset = 0;
240		mtable->csr15dir = mtable->csr15val = 0;
241
242		pr_info("%s: EEPROM default media type %s\n",
243			dev->name,
244			media & 0x0800 ? "Autosense"
245				       : medianame[media & MEDIA_MASK]);
246		for (i = 0; i < count; i++) {
247			struct medialeaf *leaf = &mtable->mleaf[i];
248
249			if ((p[0] & 0x80) == 0) { /* 21140 Compact block. */
250				leaf->type = 0;
251				leaf->media = p[0] & 0x3f;
252				leaf->leafdata = p;
253				if ((p[2] & 0x61) == 0x01)	/* Bogus, but Znyx boards do it. */
254					mtable->has_mii = 1;
255				p += 4;
256			} else {
257				leaf->type = p[1];
258				if (p[1] == 0x05) {
259					mtable->has_reset = i;
260					leaf->media = p[2] & 0x0f;
261				} else if (tp->chip_id == DM910X && p[1] == 0x80) {
262					/* Hack to ignore Davicom delay period block */
263					mtable->leafcount--;
264					count--;
265					i--;
266					leaf->leafdata = p + 2;
267					p += (p[0] & 0x3f) + 1;
268					continue;
269				} else if (p[1] & 1) {
270					int gpr_len, reset_len;
271
272					mtable->has_mii = 1;
273					leaf->media = 11;
274					gpr_len=p[3]*2;
275					reset_len=p[4+gpr_len]*2;
276					new_advertise |= get_u16(&p[7+gpr_len+reset_len]);
277				} else {
278					mtable->has_nonmii = 1;
279					leaf->media = p[2] & MEDIA_MASK;
280					/* Davicom's media number for 100BaseTX is strange */
281					if (tp->chip_id == DM910X && leaf->media == 1)
282						leaf->media = 3;
283					switch (leaf->media) {
284					case 0: new_advertise |= 0x0020; break;
285					case 4: new_advertise |= 0x0040; break;
286					case 3: new_advertise |= 0x0080; break;
287					case 5: new_advertise |= 0x0100; break;
288					case 6: new_advertise |= 0x0200; break;
289					}
290					if (p[1] == 2  &&  leaf->media == 0) {
291						if (p[2] & 0x40) {
292							u32 base15 = get_unaligned((u16*)&p[7]);
293							mtable->csr15dir =
294								(get_unaligned((u16*)&p[9])<<16) + base15;
295							mtable->csr15val =
296								(get_unaligned((u16*)&p[11])<<16) + base15;
297						} else {
298							mtable->csr15dir = get_unaligned((u16*)&p[3])<<16;
299							mtable->csr15val = get_unaligned((u16*)&p[5])<<16;
300						}
301					}
302				}
303				leaf->leafdata = p + 2;
304				p += (p[0] & 0x3f) + 1;
305			}
306			if (tulip_debug > 1  &&  leaf->media == 11) {
307				unsigned char *bp = leaf->leafdata;
308				pr_info("%s: MII interface PHY %d, setup/reset sequences %d/%d long, capabilities %02x %02x\n",
309					dev->name,
310					bp[0], bp[1], bp[2 + bp[1]*2],
311					bp[5 + bp[2 + bp[1]*2]*2],
312					bp[4 + bp[2 + bp[1]*2]*2]);
313			}
314			pr_info("%s: Index #%d - Media %s (#%d) described by a %s (%d) block\n",
315				dev->name,
316				i, medianame[leaf->media & 15], leaf->media,
317				leaf->type < ARRAY_SIZE(block_name) ? block_name[leaf->type] : "<unknown>",
318				leaf->type);
319		}
320		if (new_advertise)
321			tp->sym_advertise = new_advertise;
322	}
323}
324/* Reading a serial EEPROM is a "bit" grungy, but we work our way through:->.*/
325
326/*  EEPROM_Ctrl bits. */
327#define EE_SHIFT_CLK	0x02	/* EEPROM shift clock. */
328#define EE_CS		0x01	/* EEPROM chip select. */
329#define EE_DATA_WRITE	0x04	/* Data from the Tulip to EEPROM. */
330#define EE_WRITE_0	0x01
331#define EE_WRITE_1	0x05
332#define EE_DATA_READ	0x08	/* Data from the EEPROM chip. */
333#define EE_ENB		(0x4800 | EE_CS)
334
335/* Delay between EEPROM clock transitions.
336   Even at 33Mhz current PCI implementations don't overrun the EEPROM clock.
337   We add a bus turn-around to insure that this remains true. */
338#define eeprom_delay()	ioread32(ee_addr)
339
340/* The EEPROM commands include the alway-set leading bit. */
341#define EE_READ_CMD		(6)
342
343/* Note: this routine returns extra data bits for size detection. */
344int __devinit tulip_read_eeprom(struct net_device *dev, int location, int addr_len)
345{
346	int i;
347	unsigned retval = 0;
348	struct tulip_private *tp = netdev_priv(dev);
349	void __iomem *ee_addr = tp->base_addr + CSR9;
350	int read_cmd = location | (EE_READ_CMD << addr_len);
351
352	/* If location is past the end of what we can address, don't
353	 * read some other location (ie truncate). Just return zero.
354	 */
355	if (location > (1 << addr_len) - 1)
356		return 0;
357
358	iowrite32(EE_ENB & ~EE_CS, ee_addr);
359	iowrite32(EE_ENB, ee_addr);
360
361	/* Shift the read command bits out. */
362	for (i = 4 + addr_len; i >= 0; i--) {
363		short dataval = (read_cmd & (1 << i)) ? EE_DATA_WRITE : 0;
364		iowrite32(EE_ENB | dataval, ee_addr);
365		eeprom_delay();
366		iowrite32(EE_ENB | dataval | EE_SHIFT_CLK, ee_addr);
367		eeprom_delay();
368		retval = (retval << 1) | ((ioread32(ee_addr) & EE_DATA_READ) ? 1 : 0);
369	}
370	iowrite32(EE_ENB, ee_addr);
371	eeprom_delay();
372
373	for (i = 16; i > 0; i--) {
374		iowrite32(EE_ENB | EE_SHIFT_CLK, ee_addr);
375		eeprom_delay();
376		retval = (retval << 1) | ((ioread32(ee_addr) & EE_DATA_READ) ? 1 : 0);
377		iowrite32(EE_ENB, ee_addr);
378		eeprom_delay();
379	}
380
381	/* Terminate the EEPROM access. */
382	iowrite32(EE_ENB & ~EE_CS, ee_addr);
383	return (tp->flags & HAS_SWAPPED_SEEPROM) ? swab16(retval) : retval;
384}
385