Subject: bin/4160: fdformat transient failures
To: None <gnats-bugs@gnats.netbsd.org>
From: maximum entropy <entropy@tardis.bernstein.com>
List: netbsd-bugs
Date: 09/26/1997 05:41:42
>Number:         4160
>Category:       bin
>Synopsis:       fdformat fails when it shouldn't
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    bin-bug-people (Utility Bug People)
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Fri Sep 26 02:50:01 1997
>Last-Modified:
>Originator:     maximum entropy
>Organization:
	
>Release:        <NetBSD-current source date>19970925
>Environment:
	
System: NetBSD tardis.bernstein.com 1.2G NetBSD 1.2G (C466DE) #0: Wed Sep 24 08:31:32 EDT 1997 entropy@tardis.bernstein.com:/usr/src/sys/arch/i386/compile/C466DE i386

i386 (Pentium) with floppy drive
fdc0 at isa0 port 0x3f0-0x3f7 irq 6 drq 2
fd0 at fdc0 drive 0: 1.44MB, 80 cyl, 2 head, 18 sec

>Description:
	
Certain types of system events may cause the floppy read to be interrupted,
causing the track verify operation to fail even though the track was
properly formatted.  For example, if an xterm running fdformat is
resized, the delivery of the SIGWINCH will cause a failure.  Other events
that don't cause a signal may also cause a failure, for example setting
focus to another xterm will cause fdformat to fail most of the time.

>How-To-Repeat:
	
Start fdformat in an xterm, then resize the window a few times.
>Fix:
	
It isn't sufficient to block or ignore certain signals (see description
section)

One possible solution is to not set the FDOPT_NORETRY flag in fdformat.c.
However this makes the system drag a lot if a format operation is failing
repeatedly (e.g. bad floppy or no floppy inserted).  Also this may cause
marginal disks to format OK when it might be better to make it clear that
the disk is losing.

A somewhat better solution is to only disable the FDOPT_NORETRY flag
during the verify operation, then restore the original flags before
continuing the disk format.

--- /usr/src/usr.bin/fdformat/fdformat.c-orig	Mon Jun 16 07:48:26 1997
+++ /usr/src/usr.bin/fdformat/fdformat.c	Fri Sep 26 05:25:44 1997
@@ -91,20 +91,31 @@
 {
 	size_t tracksize;
 	off_t offset;
+	int opts, tmpopts;
+	int status;
 
 	tracksize = parms->nbps * parms->nspt; /* bytes per track */
 	offset = tracksize * (cyl * parms->ntrk + trk); /* track offset */
 
-	if (lseek(fd, offset, SEEK_SET) == (off_t) -1) {
-		putchar('E');
-		return 1;
+	if (ioctl(fd, FDIOCGETOPTS, &opts) == -1) {
+		errx(1, "cannot get floppy I/O options");
+	}
+	tmpopts = opts & ~FDOPT_NORETRY;
+	if (ioctl(fd, FDIOCSETOPTS, &tmpopts) == -1) {
+		errx(1, "cannot set floppy I/O options");
 	}
-	if (read(fd, buf, tracksize) != tracksize) {
+	if ((lseek(fd, offset, SEEK_SET) == (off_t) -1)
+	    || (read(fd, buf, tracksize) != tracksize)) {
 		putchar('E');
-		return 1;
-	} else
+		status = 1;
+	} else {
 		putchar('V');
-	return 0;
+		status = 0;
+	}
+	if (ioctl(fd, FDIOCSETOPTS, &opts) == -1) {
+		errx(1, "cannot restore floppy I/O options");
+	}
+	return status;
 }
 
 void



>Audit-Trail:
>Unformatted: