4 NE1000 / NE2000网卡(及其兼容卡)的问题
问题:在用v2.0.x启动时没有检测到PCI NE2000兼容网卡。
原因:在v2.0.30之前的ne.c驱动程序只知道基于RealTek 8029的兼容网卡的PCI ID号。在此只后才出现了使用其它PCI ID号的PCI NE2000兼容网卡,所以驱动程序无法检测这些网卡。
解决方案:最简单的方法是把Linux内核升级到v2.0.31以上版本。它可以识别五种不同的NE2000-PCI芯片的ID号,在启动或载入模块时自动检测到它们。如果你升级到了2.0.34以上版本,会有一个比原先的ISA/PCI驱动程序稍小但更高效的PCI专用NE2000驱动程序。
问题:启动时PCI NE2000兼容网卡被报告为ne1000(8比特网卡!)或者在v2.0.x下载入ne.o模块不起作用。
原因:某些PCI兼容网卡不支持字节存取(因此不是百分之百的兼容NE2000)。这使检测时被误认为NE1000网卡。
解决方案:你需要升级到v2.0.31以上版本。现在的驱动程序会检测到这种硬件Bug。
问题:PCI NE2000网卡的性能很差,即使按照性能技巧章节所说的减小了窗口大小。
原因:十多年前设计和出售的初始8390芯片的技术数据手册上提到,为了得到最高的可靠性,在每次写操作之前需要一个读操作。驱动程序能够轻易地做到这一点,但从v1.2内核时代起,缺省情况下取消了这一操作。有一个用户报告说重新使用这一“错误的特性”就可以改善廉价的PCI NE2000兼容网卡的性能。
解决方案:由于只有一个用户提出报告把它作为解决方案,不要对此寄予太大的希望。重新使用写之前的读操作可以简单地编辑linux/drivers/net/下的驱动程序文件,取消包含NE_RW_BUGFIX的那一行的注释,然后重建内核或载入相应的模块。如果这样确实有效,请给我发一封e-mail,描述性能上的差异和你所使用的网卡/芯片类型。(对ne2k-pci.c驱动程序也可以如法炮制。)
问题:ne2k-pci.c驱动程序对PCI NE2000网卡报告诸如timeout waiting for Tx RDC错误信息,无法正常工作。
原因:你的网卡或网卡到PCI总线的连接无法处理该驱动程序使用的长字I/O优化。
解决方案:首先,检查BIOS/CMOS设置,看看与PCI总线相关的计时对于可靠的操作是否过于严格了。否则,使用ISA/PCI的ne.c驱动程序(或者删除ne2k-pci.c中的#define USE_LONGIO),使你的网卡可用。
问题:没检测到ISA的即插即用NE2000网卡(如RealTek 8019)。
原因:初始的NE2000特性不支持即插即用,因此Linux的NE2000驱动程序也不支持即插即用。
解决方案:使用网卡所附的DOS配置盘取消PnP,并为该网卡设置一个指定的I/O地址和IRQ。在/etc/conf.modules里增加这样的一行options ne io=0xNNN,这里0xNNN是你为网卡设置的16进制I/O地址。(假设你使用的是模块化驱动程序;否则,在启动时使用一个ether=0,0xNNN,eth0参数。你也可以进入BIOS/CMOS设置,把IRQ从PnP改为Legacy-ISA。如果你需要为兼容其它的操作系统而保留PnP设置,那么你可以看一下isapnptools包。使用man isapnp看看它是否已经安装在你的系统上了。如果没有,浏览一下下面的连接:
ISA PNP Tools
问题:在启动检测时NE*000驱动程序报告“not found (no reset ack)”。
原因:这跟上面所说的改动有关。在证实8390处于所检测的I/O地址之后,进行重新设置。在网卡完成重新设置后,应当通知重新设置完成。你的网卡没有通知,所以驱动程序认为不存在NE网卡。
解决方案:你可以在启动时使用一个未被使用的mem_end16进制值0xbad,告诉驱动程序你有一个坏网卡。在使用0xbad撤消时你必须为网卡提供一个非零的I/O地址。例如,在0x340的网卡不响应重新设置,则使用如下方法:
LILO: linux ether=0,0x340,0,0xbad,eth0
这样,即使你的网卡不响应重新设置,网卡检测还能继续下去。如果你是以模块方式使用驱动程序,那么可以象提供I/O地址一样提供选项bad=0xbad。
问题:NE*000网卡使机器在第一次网络访问时死机。
原因:这个问题从早期的1.1.57内核到现在都出现过,而且只在有限的几种软件配置的兼容网卡上出现。看来是需要用某些特殊的方法来初始化它们。
解决方案:有几个人报告在热启动(即loadlin或Ctrl-Alt-Del)Linux之前,运行提供的DOS软件配置程序或提供的DOS驱动程序可以使网卡工作。这表明这些卡需要以某种特殊的方式初始化,与当前的Linux驱动程序稍有区别。
问题:在0x360的NE*000以太网卡没有检测到。
原因:你的NE2000网卡在I/O空间占据了0x20个字节,使它与0x378处的并口发生冲突。其它可能的设备是0x370处的第二个软盘控制器(如果有的话),以及0x376--0x377处的第二个IDE控制器。如果该口已被其它驱动程序注册,内核将不再进行检测。
解决方案:把你的网卡移到0x280, 0x340, 0x320一类的地址,或者在编译时不支持并行打印机。
问题:每次打印时网络都断开(NE2000)。
原因:与上一个问题相同,但你的内核比较老,不支持对重叠I/O区域的检查。使用如上的解决方案,有空时获取一个新的内核。
问题:没检测到0xNNN: 00 00 C5 ... 处的NE*000以太网卡。(非法标识yy zz)
原因:首先,你是否在地址0xNNN处有一个NE1000或NE2000网卡?如果有,报告的硬件地址是否象一个合法地址?如果是的话,那么你的NE*000兼容网卡很差劲。所有的 NE*000兼容网卡都假定网卡上的SA PROM的第14和15字节为0x57。而你的网卡不是这样 -- 它的值为“yy zz”。
解决方案:有两种解决方法。最简单的方法就是如上所述的“no reset ack” 解决方案,使用一个0xbad的mem_end值。这样在提供一个非零的I/O地址时就可以忽略标识检查。此方法无需重新编译内核。
第二种方法(对黑客)需要修改驱动程序,并重新编译内核(或模块)。在驱动程序(/usr/src/linux/drivers/net/ne.c)的42行有一个“Hall of Shame”列表。这个表是用来检测那些差劲的兼容网卡的。例如,DFI网卡在PROM的前三个字节使用“DFI”,而不是象要求的那样在第14和15字节使用0x57。
问题:机器在启动时出现“8390...”或“WD....”信息后死机。拔掉NE2000就好了。
解决方案:把你的NE2000地址改为0x340一类的地址。此外,你可以在和“ether=”参数一起使用“reserve=”启动参数,保护网卡不受其它设备驱动程序检测的影响。
原因:你的NE2000兼容网卡兼容性不好。一个激活的NE2000是个无底洞,会使其它的驱动程序陷在其空间内进行自动检测。把NE2000改到一个不常用的地址就可以从其它的自动检测中消除这一陷阱,机器也就可以启动了。
问题:机器启动时在进行SCSI检测时死机。
原因:这个问题跟上面的一样,改变以太网卡的地址,或使用reserve/ether启动参数。
问题:机器启动时在进行声卡检测时死机。
原因:不可能,实际上是发生在静默方式的SCSI检测过程中,与上面的问题一样。
问题:启动时检测不到NE2000 - 根本就没有启动信息。
解决方案:因为造成检测不到的原因很多,所以没有“神奇的解决方案”。下面列出了可能有所帮助的一些措施。
1) 构建一个只包含需要的设备驱动程序的内核。证实你确实是从新内核启动的。忘记运行lilo等会使你从老的内核启动。(仔细观察启动时报告的构建时间/日期。)听起来很明显,但我们以前都犯过这个错。通过检查System.map文件里ne_probe一类的名称,确定驱动程序已包含在新的内核里。
2) 仔细观察启动信息。看看它是否提及正在进行诸如“NE*000 probe at 0xNNN: not found (blah blah)”一类的ne2k检测,或者就是静悄悄地失败了。这里的区别很大。使用dmesg|more在登录后浏览启动信息,或者在启动完成显示登录提示符时使用Shift-PgUp卷回屏幕。
3) 启动后,执行cat /proc/ioports,证实网卡要求的全部I/O空间是空的。如果网卡在0x300,那么ne2k驱动程序要求的空间为0x300-0x31f。如果其它设备的驱动程序注册了其中的一个口,就不会对该地址进行检测,而是静悄悄地检测下一个要检测的地址。常见的情况是lp驱动程序保留了0x378,或者第二个IDE通道保留了0x376,这就使ne驱动程序停止检测0x360-0x380。
4) 与上面一样执行cat /proc/interrupts。确定没有其它设备注册了你为以太网卡设置的中断。这种情况下,检测可以进行,以太网卡驱动程序会在启动时大声抱怨无法得到所要求的IRQ中断线。
5) 如果你还为驱动程序静悄悄地失败而苦恼,那么编辑并给检测增加一些printk()。比如,对于ne2k,你可以在linux/drivers/net/ne.c中增加/删除某些行(用 “+”或“-”表示),如下所示:
--------------------------------------------------------------------------------
int reg0 = inb_p(ioaddr);
+ printk("NE2k probe - now checking %x\n",ioaddr);
- if (reg0 == 0xFF)
+ if (reg0 == 0xFF) {
+ printk("NE2k probe - got 0xFF (vacant I/O port)\n");
return ENODEV;
+ }
--------------------------------------------------------------------------------
那么它就会输出检查的每一个口地址信息,你可以看到你的网卡地址是否被检测了。