Date: Fri, 9 Aug 1996 00:53:05 -0400 (EDT) From: Bill Paul <wpaul@skynet.ctr.columbia.edu> To: current@freebsd.org Subject: wd.c/ATAPI patch -- testers wanted Message-ID: <199608090453.AAA21823@skynet.ctr.columbia.edu>
next in thread | raw e-mail | index | archive | help
Tonight I blew a few hours playing with the ATAPI support. The result
was the small patch appended to this message, which seems to make the
detection of ATAPI devices happen much more reliably. This patch is
for 2.2-current.
The machine I used for testing is a Gateway 2000 Pentium 200 Mhz
with 64MB or RAM, 2.5GB Western Digital IDE disk drive, Toshiba 8x ATAPI/IDE
CD-ROM drive, primary and secondary PCI-based on-board IDE controllers.
(Default configuration is IDE hard disk as only disk on primary controller
and CD-ROM as master on secondary controller.)
The problems I had with this system were as follows:
- The kernel fails to find the ATAPI CD-ROM drive when it's jumpered
as the master device on the secondary controller. Windoze NT is able
to handle this configuration with no trouble.
- With the GENERIC configuration and the drive jumpered as the slave
on the secondary controller, the kernel finds the drive but it also
finds a phantom wd2. This hoses sysinstall when booting from the
installation floppy (it attempts to open the phantom drive and
wedges).
In the first case, the problem is that wdprobe() decides that there
is no wdc1 controller because the code near the end which checks the
error status of the drives bails out incorrectly. The comments say
that some controllers return 0x81 and then, when the DRV bit is set,
they return 0x01 later. In my case, the check returns 0x81 both times.
The comments also say that 0x81 means drive 0 okay and drive 1 failed.
This is more or less correct (we have a master drive and no slave),
but the code bails out unless it gets 0x01 again. My fix was to
honor the second 0x81 as a valid response. This was a one line change.
In the second case, the problem is in the wgetctlr(). It checks wd_status
(among other things) in search of a WDSC_READY state. It turns out that
with my hardware, the controller will bogusly return WDSC_READY on the
empty master slot when the CD-ROM is jumpered as a slave. If you check
wd_status a second time, a different value is returned. My fix was to
read the wd_status location once and discard the value before reading
it again as part of the actual test. I'm not really sure about this one
but it seems to do the job.
With these two small changes, I was able to get the CD-ROM detected
reliably in a number of different hardware configurations:
- master on secondary controller with another IDE disk as slave
- slave as secondary controller with another IDE disk as master
- master on secondary controller alone
- slave on second controller alone
- only drive on secondary controller (no jumper in either master
or slave position)
- slave on primary controller with another IDE disk as master
- master on primary controller with another IDE disk as slave
I couldn't really check the CD-ROM on the primary controller alone since
then I wouldn't have a boot disk. I would also have liked to test the
drive with a different controller, but I didn't have one handy that I
could configure for the secondary address and IRQ.
I'd like some people who have IDE/ATAPI CD-ROMs exhibiting similar
problems to test this patch to see if it makes any difference. Since
I need this to make my machines work right, I'll be committing this
to -current eventually if nobody offers any objections.
-Bill
--
=============================================================================
-Bill Paul (212) 854-6020 | System Manager, Master of Unix-Fu
Work: wpaul@ctr.columbia.edu | Center for Telecommunications Research
Home: wpaul@skynet.ctr.columbia.edu | Columbia University, New York City
=============================================================================
"If you're ever in trouble, go to the CTR. Ask for Bill. He will help you."
=============================================================================
*** wd.c.old Sat Jul 27 15:01:10 1996
--- wd.c Thu Aug 8 23:01:00 1996
***************
*** 410,417 ****
/* Get status for drive 1 */
du->dk_error = inb(du->dk_port + wd_error);
/* printf("Error (drv 1) : %x\n", du->dk_error); */
!
! if(du->dk_error != 0x01)
goto nodevice;
} else /* drive 0 fail */
goto nodevice;
--- 410,421 ----
/* Get status for drive 1 */
du->dk_error = inb(du->dk_port + wd_error);
/* printf("Error (drv 1) : %x\n", du->dk_error); */
! /*
! * Sometimes (apparently mostly with ATAPI
! * drives involved) 0x81 really means 0x81
! * (drive 0 OK, drive 1 failed).
! */
! if(du->dk_error != 0x01 && du->dk_error != 0x81)
goto nodevice;
} else /* drive 0 fail */
goto nodevice;
***************
*** 1520,1525 ****
--- 1524,1533 ----
return (1);
outb(du->dk_port + wd_sdh, WDSD_IBM | (du->dk_unit << 4));
DELAY(5000); /* usually unnecessary; drive select is fast */
+ /*
+ * Do this twice: may get a false WDCS_READY the first time.
+ */
+ inb(du->dk_port + wd_status);
if ((inb(du->dk_port + wd_status) & (WDCS_BUSY | WDCS_READY))
!= WDCS_READY
|| wdcommand(du, 0, 0, 0, 0, WDCC_RESTORE | WD_STEP) != 0
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?199608090453.AAA21823>
