Andrew, You had mentioned at OLS I should send you this patch even though jgarzik (maintainer) has rejected them. Jeff rejected them because the patches can delay up to 1.5ms (originally 2.5ms) while interrupts are blocked. Maybe now one could use msleep() or something like that? I "maintain" this patch in the parisc-linux CVS tree because it Works For Me (tm). AFAIK, no one has submitted better fixes to date. This patch is also available from: ftp://ftp.parisc-linux.org/patches/diff-tulip_phy_reset-03 thanks, grant Index: drivers/net/tulip/media.c =================================================================== RCS file: /var/cvs/linux-2.6/drivers/net/tulip/media.c,v retrieving revision 1.10.10.1 diff -u -p -r1.10.10.1 media.c --- drivers/net/tulip/media.c 24 Nov 2003 03:06:39 -0000 1.10.10.1 +++ drivers/net/tulip/media.c 24 Nov 2003 05:33:35 -0000 @@ -43,8 +43,10 @@ static const unsigned char comet_miireg2 /* MII transceiver control section. Read and write the MII registers using software-generated serial - MDIO protocol. See the MII specifications or DP83840A data sheet - for details. */ + MDIO protocol. + See IEEE 802.3-2002.pdf (Section 2, Chapter "22.2.4 Management functions") + or DP83840A data sheet for more details. + */ int tulip_mdio_read(struct net_device *dev, int phy_id, int location) { @@ -271,13 +273,29 @@ void tulip_select_media(struct net_devic int reset_length = p[2 + init_length]; misc_info = (u16*)(reset_sequence + reset_length); if (startup) { + int timeout = 10; /* max 1 ms */ outl(mtable->csr12dir | 0x100, ioaddr + CSR12); for (i = 0; i < reset_length; i++) outl(reset_sequence[i], ioaddr + CSR12); + + /* flush posted writes */ + inl(ioaddr + CSR12); + + /* Sect 3.10.3 in DP83840A.pdf (p39) */ + udelay(500); + + /* Section 4.2 in DP83840A.pdf (p43) */ + /* and IEEE 802.3 "22.2.4.1.1 Reset" */ + while (timeout-- && + (tulip_mdio_read (dev, phy_num, MII_BMCR) & BMCR_RESET)) + udelay(100); } for (i = 0; i < init_length; i++) outl(init_sequence[i], ioaddr + CSR12); + + inl(ioaddr + CSR12); /* flush posted writes */ } + tmp_info = get_u16(&misc_info[1]); if (tmp_info) tp->advertising[phy_num] = tmp_info | 1; - : send the line "unsubscribe linux-net" in the body of a message to majordomo@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html