From owner-freebsd-multimedia Tue Mar 24 19:51:17 1998 Return-Path: Received: (from majordom@localhost) by hub.freebsd.org (8.8.8/8.8.8) id TAA25762 for freebsd-multimedia-outgoing; Tue, 24 Mar 1998 19:51:17 -0800 (PST) (envelope-from owner-freebsd-multimedia@FreeBSD.ORG) Received: from watermarkgroup.com (lor.watermarkgroup.com [207.202.73.33]) by hub.freebsd.org (8.8.8/8.8.8) with SMTP id TAA25757 for ; Tue, 24 Mar 1998 19:51:14 -0800 (PST) (envelope-from luoqi@watermarkgroup.com) Received: by watermarkgroup.com (4.1/SMI-4.1) id AA28812; Tue, 24 Mar 98 22:48:12 EST Date: Tue, 24 Mar 98 22:48:12 EST From: luoqi@watermarkgroup.com (Luoqi Chen) Message-Id: <9803250348.AA28812@watermarkgroup.com> To: freebsd-multimedia@FreeBSD.ORG, scottm@cs.ucla.edu Subject: Re: NEC 276 CDrom drive Sender: owner-freebsd-multimedia@FreeBSD.ORG Precedence: bulk X-Loop: FreeBSD.org > I brought this up on this list a few months ago, and now with a minor > lull in my courses, I did some debugging. I'd been getting "unknown > phase" errors and was told that this was due to latency in the controller. > > It's not. It's due to a strong predicate in atapi.c. I changed > > #define PHASE_COMPLETED (ARI_IN | ARI_CMD) > > to > > #define PHASE_COMPLETED (ARI_CMD) > > and the unknown phase (the more common problem for me) goes away. > Apparently, the controller doesn't assert ARI_IN when the ATAPI_MODE_SENSE > command is done. > > Question: Is this change to PHASE_COMPLETED, albeit a weaker predicate, > safe? And can someone commit this change to -current? You can't do this. According to spec, ARI_IN and ARI_CMD both have to be asserted when data transfer is done. I have a NEC 273/4.21 drive, and I saw the same message during bootup. Signal timing for these NEC drives doesn't exactly follow the spec: when data transfer is done, the drive should assert IO/CMD first, then deassert ARQ and BSY, then assert INTRQ. Try the following patch: Index: atapi.c =================================================================== RCS file: /fun/cvs/src/sys/i386/isa/atapi.c,v retrieving revision 1.24 diff -u -r1.24 atapi.c --- atapi.c 1998/03/01 18:57:27 1.24 +++ atapi.c 1998/03/24 07:48:05 @@ -711,7 +711,9 @@ { u_char ireason; u_short len, i; + int retry = 100; +again: if (atapi_wait (ata->port, 0) < 0) { ac->result.status = inb (ata->port + AR_STATUS); ac->result.error = inb (ata->port + AR_ERROR); @@ -734,8 +736,13 @@ ac->result.status, ARS_BITS, ac->result.error, AER_BITS); } - switch ((ireason & (ARI_CMD | ARI_IN)) | (ac->result.status & ARS_DRQ)) { + switch ((ireason & (ARI_CMD|ARI_IN)) | (ac->result.status & ARS_DRQ)) { default: + /* we could be between phases for immediate requests */ + if (!ac->callback && retry--) { + DELAY(10); + goto again; + } printf ("atapi%d.%d: unknown phase\n", ata->ctrlr, ac->unit); ac->result.code = RES_ERR; break; @@ -948,20 +955,13 @@ /* Send packet command. */ atapi_send_cmd (ata, ac); - /* Wait for data i/o phase. */ - for (cnt=20000; cnt>0; --cnt) - if (((inb (ata->port + AR_IREASON) & (ARI_CMD | ARI_IN)) | - (inb (ata->port + AR_STATUS) & ARS_DRQ)) != PHASE_CMDOUT) - break; - - /* Do all needed i/o. */ - while (atapi_io (ata, ac)) - /* Wait for DRQ deassert. */ + do { for (cnt=2000; cnt>0; --cnt) { - if (! (inb (ata->port + AR_STATUS) & ARS_DRQ)) + u_char s = inb(ata->port + AR_STATUS); + if ((s & (ARS_DRQ | ARS_BSY)) == ARS_BSY) break; - DELAY(10); } + } while (atapi_io(ata, ac)); } return (ac->result); } > > -scooter > -- > Scott Michel | In life, there are sheep and there are > UCLA Computer Science | wolves. > PhD Graduate Student | ... And I don't bleed ... > > To Unsubscribe: send mail to majordomo@FreeBSD.org > with "unsubscribe freebsd-multimedia" in the body of the message > -lq To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-multimedia" in the body of the message