Date: Sat, 20 Dec 2008 03:20:16 -0600 (CST) From: "James R. Van Artsdalen" <james@jrv.org> To: FreeBSD-gnats-submit@FreeBSD.org Subject: kern/129784: [patch] SATA port multiplier disk detect bugs in -current (svn186316) Message-ID: <200812200920.mBK9KG9m074530@fearless.housenet.jrv> Resent-Message-ID: <200812201030.mBKAU1CO084570@freefall.freebsd.org>
next in thread | raw e-mail | index | archive | help
>Number: 129784 >Category: kern >Synopsis: [patch] SATA port multiplier disk detect bugs in -current (svn186316) >Confidential: no >Severity: non-critical >Priority: low >Responsible: freebsd-bugs >State: open >Quarter: >Keywords: >Date-Required: >Class: sw-bug >Submitter-Id: current-users >Arrival-Date: Sat Dec 20 10:30:00 UTC 2008 >Closed-Date: >Last-Modified: >Originator: James R. Van Artsdalen >Release: FreeBSD 8 -current, svn186316 >Organization: Institute for Applied Stellar Nucleosynthesis >Environment: System: FreeBSD fearless 8 -current svn186316 #0: Fri Dec 24 01:47:55 CST 2004 james@jrv.org:/usr/src/sys/amd64/compile/GENERIC amd64 >Description: This only affects Silicon Image host controllers. It was only tested with a 3132. I have found two bugs in the port multiplier code and a place where an added delay is both necessary and sufficient to make my setup work, even though I can't explain why. With the included patch my setup, with a Sil3132 host controller, always detects the drives in my Sil3726 based port-multiplier enclosures. There are other problems trying to format and use the disks, but at least this may let people get past disk detection. >How-To-Repeat: Attach a port multiplier enclosure to a Silicon Image host adapter. Some or all disks in the enclosure may not be seen. >Fix: The first change in ata_siiprb_issue_cmd() increases the timeout count from 10,000 to 31,000 counts. When a soft reset is issued to a port multiplier disk port this loop may have to wait for the hard disk to spin up. I consistently saw 15,000 counts as needed by experiment; assuming counts are milliseconds then 31,000 is what ATA calls for. Note that currently empty disk ports behind a port multiplier are detected by letting this loop time out; i.e., an empty port multiplier enclosure can lengthen boot by 2.5 minutes. Some other strategy for disk detection might be needed later (the PHY probably is a good approach). The second change in ata_siiprb_issue_cmd() fixes a typo: failure was being returned if a command took more than 1,000 counts, even if it completed within the allotted 10,000 counts. The last change in ata_siiprb_softreset() is a delay that is mysteriously turns out to be necessary. I don't know why, how much or how little is needed. Hardware is like that sometimes. /usr/src-current# svn di Index: sys/dev/ata/chipsets/ata-siliconimage.c =================================================================== --- sys/dev/ata/chipsets/ata-siliconimage.c (revision 186316) +++ sys/dev/ata/chipsets/ata-siliconimage.c (working copy) @@ -679,7 +679,7 @@ ATA_OUTL(ctlr->r_res2, 0x1c04 + offset, prb_bus >> 32); /* poll for command finished */ - for (timeout = 0; timeout < 10000; timeout++) { + for (timeout = 0; timeout < 31000; timeout++) { DELAY(1000); if ((status = ATA_INL(ctlr->r_res2, 0x1008 + offset)) & 0x00010000) break; @@ -687,7 +687,7 @@ // SOS XXX ATA_OUTL(ctlr->r_res2, 0x1008 + offset, 0x00010000); ATA_OUTL(ctlr->r_res2, 0x1008 + offset, 0x08ff08ff); - if (timeout >= 1000) + if (timeout >= 31000) return EIO; if (bootverbose) @@ -761,6 +761,18 @@ prb->control = htole16(0x0080); prb->fis[1] = port & 0x0f; + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + ata_udelay(150000); + /* issue soft reset */ if (ata_siiprb_issue_cmd(dev)) return -1; /usr/src-current# >Release-Note: >Audit-Trail: >Unformatted:
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200812200920.mBK9KG9m074530>