diff options
author | phk <phk@FreeBSD.org> | 1999-11-27 14:35:22 +0000 |
---|---|---|
committer | phk <phk@FreeBSD.org> | 1999-11-27 14:35:22 +0000 |
commit | a3e4a9264f20e4e36cae6f1bfb2051210dd3ae89 (patch) | |
tree | c1b9d5305759ca272dd2817a3d49fc620d4f9b8a /usr.sbin | |
parent | ba79ac5ee3fabeaeb91c492c7e0b3928a226329a (diff) | |
download | FreeBSD-src-a3e4a9264f20e4e36cae6f1bfb2051210dd3ae89.zip FreeBSD-src-a3e4a9264f20e4e36cae6f1bfb2051210dd3ae89.tar.gz |
Remove bad144 program.
Diffstat (limited to 'usr.sbin')
-rw-r--r-- | usr.sbin/Makefile | 1 | ||||
-rw-r--r-- | usr.sbin/bad144/Makefile | 10 | ||||
-rw-r--r-- | usr.sbin/bad144/bad144.8 | 192 | ||||
-rw-r--r-- | usr.sbin/bad144/bad144.c | 612 |
4 files changed, 0 insertions, 815 deletions
diff --git a/usr.sbin/Makefile b/usr.sbin/Makefile index 5c6ae1c..a2d3c3b 100644 --- a/usr.sbin/Makefile +++ b/usr.sbin/Makefile @@ -130,7 +130,6 @@ SUBDIR+=elf2exe SUBDIR+=apm \ apmconf \ apmd \ - bad144 \ boot0cfg \ btxld \ i4b \ diff --git a/usr.sbin/bad144/Makefile b/usr.sbin/bad144/Makefile deleted file mode 100644 index 457fda7..0000000 --- a/usr.sbin/bad144/Makefile +++ /dev/null @@ -1,10 +0,0 @@ -# @(#)Makefile 8.1 (Berkeley) 6/6/93 - -PROG= bad144 -SRCS= bad144.c dkcksum.c -MAN8= bad144.8 -MLINKS= bad144.8 ../bad144.8 -MANSUBDIR=/${MACHINE_ARCH} -.PATH: ${.CURDIR}/../../sbin/disklabel - -.include <bsd.prog.mk> diff --git a/usr.sbin/bad144/bad144.8 b/usr.sbin/bad144/bad144.8 deleted file mode 100644 index 9be46e6..0000000 --- a/usr.sbin/bad144/bad144.8 +++ /dev/null @@ -1,192 +0,0 @@ -.\" Copyright (c) 1980, 1988, 1991, 1993 -.\" The Regents of the University of California. All rights reserved. -.\" -.\" Redistribution and use in source and binary forms, with or without -.\" modification, are permitted provided that the following conditions -.\" are met: -.\" 1. Redistributions of source code must retain the above copyright -.\" notice, this list of conditions and the following disclaimer. -.\" 2. Redistributions in binary form must reproduce the above copyright -.\" notice, this list of conditions and the following disclaimer in the -.\" documentation and/or other materials provided with the distribution. -.\" 3. All advertising materials mentioning features or use of this software -.\" must display the following acknowledgement: -.\" This product includes software developed by the University of -.\" California, Berkeley and its contributors. -.\" 4. Neither the name of the University nor the names of its contributors -.\" may be used to endorse or promote products derived from this software -.\" without specific prior written permission. -.\" -.\" THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND -.\" ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE -.\" IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE -.\" ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE -.\" FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL -.\" DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS -.\" OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) -.\" HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT -.\" LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY -.\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF -.\" SUCH DAMAGE. -.\" -.\" @(#)bad144.8 8.1 (Berkeley) 6/6/93 -.\" $FreeBSD$ -.\" -.Dd May 13, 1995 -.Dt BAD144 8 -.Os BSD 4 -.Sh NAME -.Nm bad144 -.Nd read/write dec standard 144 bad sector information -.Sh SYNOPSIS -.Nm bad144 -.Op Fl c -.Op Fl f -.Op Fl v -.Ar disk -.Oo -.Ar sno -.Op Ar bad ... -.Oc -.Nm bad144 -.Fl a -.Op Fl c -.Op Fl f -.Op Fl v -.Ar disk -.Op Ar bad ... -.Nm bad144 -.Op Fl s -.Op Fl v -.Ar disk -.Sh DESCRIPTION -.Nm Bad144 -can be used to inspect the information stored on a disk that is used by -the disk drivers to implement bad sector forwarding. -.Pp -Available options: -.Pp -.Bl -tag -width Ds -.It Fl a -The argument list consists of new bad sectors to be added to an existing -list. -The new sectors are sorted into the list, -which must have been in order. -Replacement sectors are moved to accommodate the additions; -the new replacement sectors are cleared. -.It Fl c -Forces an attempt to copy the old sector to the replacement, -and may be useful when replacing an unreliable sector. -.It Fl f -For a RP06, RM03, RM05, Fujitsu Eagle, -or -.Tn SMD -disk on a Massbus, the -.Fl f -option may be used to mark the new bad sectors as ``bad'' -by reformatting them as unusable sectors. -This option is -.Em required unless -the sectors have already been marked bad, -or the system will not be notified that it should use the replacement sector. -This option may be used while running multiuser; it is no longer necessary -to perform format operations while running single-user. -.It Fl s -The entire disk is scanned for bad blocks. -.It Fl v -The entire process is described as it happens in gory detail if -.Fl v -(verbose) is given. -.El -.Pp -The format of -the information is specified by -.Tn DEC -standard 144, as follows. -The bad sector information is located in the first 5 even numbered sectors -of the last track of the disk pack. There are five identical copies of -the information, described by the -.Ar dkbad -structure. -.Pp -Replacement sectors are allocated starting with the first sector before -the bad sector information and working backwards towards the beginning -of the disk. A maximum of 126 bad sectors are supported. The position -of the bad sector in the bad sector table determines the replacement -sector to which it corresponds. -The bad sectors must be listed in ascending order. -.Pp -The bad sector information and replacement sectors are conventionally -only accessible through the ``c'' file system partition of the disk. If -that partition is used for a file system, the user is responsible for -making sure that it does not overlap the bad sector information or any -replacement sectors. -Thus, one track plus 126 sectors must be reserved to allow use -of all of the possible bad sector replacements. -.Pp -The bad sector structure is as follows: -.Bd -literal -struct dkbad { - long bt_csn; /* cartridge serial number */ - u_short bt_mbz; /* unused; should be 0 */ - u_short bt_flag; /* -1 => alignment cartridge */ - struct bt_bad { - u_short bt_cyl; /* bad sector cylinder number */ - u_short bt_trksec; /* track and sector number */ - } bt_bad[126]; -}; -.Ed -.Pp -Unused slots in the -.Ar bt_bad -array are filled with all bits set, a putatively -illegal value. -.Pp -.Nm Bad144 -is invoked by giving a device name (e.g. hk0, hp1, etc.). -With no optional arguments -it reads the first sector of the last track -of the corresponding disk and prints out the bad sector information. -It issues a warning if the bad sectors are out of order. -.Nm Bad144 -may also be invoked with a serial number for the pack and a list -of bad sectors. -It will write the supplied information into all copies -of the bad-sector file, replacing any previous information. -Note, however, that -.Nm bad144 -does not arrange for the specified sectors to be marked bad in this case. -This procedure should only be used to restore known bad sector information which -was destroyed. -.Pp -It is no longer necessary to reboot to allow the kernel -to reread the bad-sector table from the drive. -.Sh SEE ALSO -.Xr badsect 8 -.Sh BUGS -It should be possible to format disks on-line under -.Tn UNIX . -.Pp -It should be possible to mark bad sectors on drives of all type. -.Pp -On an 11/750, -the standard bootstrap drivers used to boot the system do -not understand bad sectors, -handle -.Tn ECC -errors, or the special -.Tn SSE -(skip sector) errors of RM80-type disks. -This means that none of these errors can occur when reading the file -.Pa /kernel -to boot. Sectors 0-15 of the disk drive -must also not have any of these errors. -.Pp -The drivers which write a system core image on disk after a crash do not -handle errors; thus the crash dump area must be free of errors and bad -sectors. -.Sh HISTORY -The -.Nm -command appeared in -.Bx 4.1 . diff --git a/usr.sbin/bad144/bad144.c b/usr.sbin/bad144/bad144.c deleted file mode 100644 index 9929c09..0000000 --- a/usr.sbin/bad144/bad144.c +++ /dev/null @@ -1,612 +0,0 @@ -/* - * Copyright (c) 1980, 1986, 1988, 1993 - * The Regents of the University of California. All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions - * are met: - * 1. Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * 2. Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * 3. All advertising materials mentioning features or use of this software - * must display the following acknowledgement: - * This product includes software developed by the University of - * California, Berkeley and its contributors. - * 4. Neither the name of the University nor the names of its contributors - * may be used to endorse or promote products derived from this software - * without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE - * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE - * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE - * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL - * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS - * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) - * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT - * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY - * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF - * SUCH DAMAGE. - */ - -#ifndef lint -static const char copyright[] = -"@(#) Copyright (c) 1980, 1986, 1988, 1993\n\ - The Regents of the University of California. All rights reserved.\n"; -#endif /* not lint */ - -#ifndef lint -#if 0 -static char sccsid[] = "@(#)bad144.c 8.2 (Berkeley) 4/27/95"; -#endif -static const char rcsid[] = - "$FreeBSD$"; -#endif /* not lint */ - -/* - * bad144 - * - * This program prints and/or initializes a bad block record for a pack, - * in the format used by the DEC standard 144. - * It can also add bad sector(s) to the record, moving the sector - * replacements as necessary. - * - * It is preferable to write the bad information with a standard formatter, - * but this program will do. - * - * RP06 sectors are marked as bad by inverting the format bit in the - * header; on other drives the valid-sector bit is cleared. - */ -#include <sys/param.h> -#include <sys/dkbad.h> -#include <sys/ioctl.h> -#include <sys/file.h> -#include <sys/disklabel.h> -#include <ufs/ffs/fs.h> - -#include <err.h> -#include <paths.h> -#include <stdio.h> -#include <stdlib.h> -#include <string.h> -#include <unistd.h> - -#define RETRIES 10 /* number of retries on reading old sectors */ - -int fflag, add, copy, verbose, nflag, sflag; -int dups; -int badfile = -1; /* copy of badsector table to use, -1 if any */ -#define MAXSECSIZE 1024 -struct dkbad curbad, oldbad; -#define DKBAD_MAGIC 0x4321 - -daddr_t size; -struct disklabel *dp; -char *name; - -u_short dkcksum __P((struct disklabel *lp)); - -int main __P((int argc, char *argv[])); -void blkzero __P((int f, daddr_t sn)); -int compare __P((const void *cvb1, const void *cvb2)); -daddr_t badsn __P((struct bt_bad *bt)); -daddr_t getold __P((int f, struct dkbad *bad)); -int blkcopy __P((int f, daddr_t s1, daddr_t s2)); -void shift __P((int f, int new, int old)); -int checkold __P((struct dkbad *oldbad)); -static void usage __P((void)); - -void -bad_scan(argc, argv, dp, f, bstart, bend) - int *argc; - char ***argv; - struct disklabel *dp; - int f; - daddr_t bstart,bend; -{ - int curr_sec, n; - int spc = dp->d_secpercyl; - int ss = dp->d_secsize; - int trk = dp->d_nsectors; - int i; - char **nargv,*buf; - int nargc; - - setbuf(stdout, NULL); - setbuf(stderr, NULL); - - nargv = (char **)malloc(sizeof *nargv * DKBAD_MAXBAD); - if (!nargv) - errx(20,"malloc failed"); - i = 1; - n = ioctl(f,DIOCSBADSCAN,&i); - if (n < 0) - warn("couldn't set disk in \"badscan\" mode"); - nargc = *argc; - memcpy(nargv,*argv,nargc * sizeof nargv[0]); - - buf = alloca((unsigned)(trk*ss)); - if (buf == (char *)NULL) - errx(20,"alloca failed"); - - /* scan the entire disk a sector at a time. Because of all the - * clustering in the kernel, we cannot scan a track at a time, - * If we do, we may have to read twice over the block to find - * exactly which one failed, and it may not fail second time. - */ - for (curr_sec = bstart; curr_sec < size; curr_sec++) { - - if (verbose) { - if ((curr_sec % spc) == 0) - printf("\r%7d of %7u blocks (%3u%%)", - curr_sec,bend,(curr_sec*100/bend)); - } - - if (lseek(f, (off_t)ss * curr_sec, SEEK_SET) < 0) - err(4, "lseek"); - - if ((n = read(f, buf, ss)) != ss) { - if (verbose) - printf("\rBlock: %7d will be marked BAD.\n", - curr_sec); - else - warnx("found bad sector: %d", curr_sec); - sprintf(buf,"%d",curr_sec); - nargv[nargc++] = strdup(buf); - if (nargc >= DKBAD_MAXBAD) - errx(1, "too many bad sectors, can only handle %d per slice", - DKBAD_MAXBAD); - } - } - fprintf(stderr, "\n"); - nargv[nargc] = 0; - *argc = nargc; - *argv = &nargv[0]; - i = 0; - n = ioctl(f,DIOCSBADSCAN,&i); - if (n < 0) - warn("couldn't reset disk from \"badscan\" mode"); -} - -int -main(argc, argv) - int argc; - char *argv[]; -{ - register struct bt_bad *bt; - daddr_t sn, bn[DKBAD_MAXBAD]; - int i, f, nbad, new, bad, errs; - daddr_t bstart, bend; - char label[BBSIZE]; - - argc--, argv++; - while (argc > 0 && **argv == '-') { - (*argv)++; - while (**argv) { - switch (**argv) { -#if vax - case 'f': - fflag++; - break; -#endif - case 'a': - add++; - break; - case 'c': - copy++; - break; - case 'v': - verbose++; - break; - case 'n': - nflag++; - verbose++; - break; - case 's': /* scan partition */ - sflag++; - add++; - break; - default: - if (**argv >= '0' && **argv <= '4') { - badfile = **argv - '0'; - break; - } - usage(); - } - (*argv)++; - } - argc--, argv++; - } - if (argc < 1) - usage(); - if (argv[0][0] != '/') - (void)sprintf(label, "%sr%s%c", _PATH_DEV, argv[0], - 'a' + RAW_PART); - else - strcpy(label, argv[0]); - name = strdup(label); - f = open(name, !sflag && argc == 1? O_RDONLY : O_RDWR); - if (f < 0) - err(4, "%s", name); - if (read(f, label, sizeof(label)) < 0) - err(4, "read"); - for (dp = (struct disklabel *)(label + LABELOFFSET); - dp < (struct disklabel *) - (label + sizeof(label) - sizeof(struct disklabel)); - dp = (struct disklabel *)((char *)dp + 64)) - if (dp->d_magic == DISKMAGIC && dp->d_magic2 == DISKMAGIC) - break; - if (dp->d_magic != DISKMAGIC || dp->d_magic2 != DISKMAGIC) - errx(1, "bad pack magic number (pack is unlabeled)"); - if (dp->d_secsize > MAXSECSIZE || dp->d_secsize <= 0) - errx(7, "disk sector size too large/small (%u)", dp->d_secsize); - size = dp->d_secperunit; - - /* - * bstart is 0 since we should always be doing partition c of a slice - * bend is the size of the slice, less the bad block map track - * and the DKBAD_MAXBAD replacement blocks - */ - bstart = 0; - bend = size - (dp->d_nsectors + DKBAD_MAXBAD); - - if (verbose) { - printf("cyl: %u, tracks: %u, secs: %u, " - "sec/cyl: %u, start: %d, end: %d\n", - dp->d_ncylinders, dp->d_ntracks, dp->d_nsectors, - dp->d_secpercyl, bstart, bend); - } - - argc--; - argv++; - - if (sflag) - bad_scan(&argc,&argv,dp,f,bstart,bend); - - if (argc == 0) { - sn = getold(f, &oldbad); - printf("bad block information at sector %d in %s:\n", - sn, name); - printf("cartridge serial number: %d(10)\n", oldbad.bt_csn); - switch (oldbad.bt_flag) { - - case (u_short)-1: - printf("alignment cartridge\n"); - break; - - case DKBAD_MAGIC: - break; - - default: - printf("bt_flag=%x(16)?\n", oldbad.bt_flag); - break; - } - bt = oldbad.bt_bad; - for (i = 0; i < DKBAD_MAXBAD; i++) { - bad = (bt->bt_cyl<<16) + bt->bt_trksec; - if (bad < 0) - break; - printf("sn=%d, cn=%d, tn=%d, sn=%d\n", badsn(bt), - bt->bt_cyl, bt->bt_trksec>>8, bt->bt_trksec&0xff); - bt++; - } - (void) checkold(&oldbad); - exit(0); - } - if (add) { - /* - * Read in the old badsector table. - * Verify that it makes sense, and the bad sectors - * are in order. Copy the old table to the new one. - */ - (void) getold(f, &oldbad); - i = checkold(&oldbad); - if (verbose) - printf("Had %d bad sectors, adding %d\n", i, argc); - if (i + argc > DKBAD_MAXBAD) { - printf("bad144: not enough room for %d more sectors\n", - argc); - printf("limited to %d by information format\n", - DKBAD_MAXBAD); - exit(1); - } - curbad = oldbad; - } else { - curbad.bt_csn = atoi(*argv++); - argc--; - curbad.bt_mbz = 0; - curbad.bt_flag = DKBAD_MAGIC; - if (argc > DKBAD_MAXBAD) { - printf("bad144: too many bad sectors specified\n"); - printf("limited to %d by information format\n", - DKBAD_MAXBAD); - exit(1); - } - i = 0; - } - errs = 0; - new = argc; - while (argc > 0) { - sn = atoi(*argv++); - argc--; - if (sn < 0 || sn >= bend) { - printf("%d: out of range [0,%d) for disk %.*s\n", - sn, bend, (int)sizeof(dp->d_typename), - dp->d_typename); - errs++; - continue; - } - bn[i] = sn; - curbad.bt_bad[i].bt_cyl = sn / (dp->d_nsectors*dp->d_ntracks); - sn %= (dp->d_nsectors*dp->d_ntracks); - curbad.bt_bad[i].bt_trksec = - ((sn/dp->d_nsectors) << 8) + (sn%dp->d_nsectors); - i++; - } - if (errs) - exit(1); - nbad = i; - while (i < DKBAD_MAXBAD) { - curbad.bt_bad[i].bt_trksec = DKBAD_NOTRKSEC; - curbad.bt_bad[i].bt_cyl = DKBAD_NOCYL; - i++; - } - if (add) { - /* - * Sort the new bad sectors into the list. - * Then shuffle the replacement sectors so that - * the previous bad sectors get the same replacement data. - */ - qsort(curbad.bt_bad, nbad, sizeof (struct bt_bad), compare); - if (dups) - errx(3, - "bad sectors have been duplicated; can't add existing sectors"); - shift(f, nbad, nbad-new); - } - if (badfile == -1) - i = 0; - else - i = badfile * 2; - for (; i < 10 && i < dp->d_nsectors; i += 2) { - if (lseek(f, (off_t)dp->d_secsize * (size - dp->d_nsectors + i), - SEEK_SET) < 0) - err(4, "lseek"); - if (verbose) - printf("write badsect file at %u\n", - size - dp->d_nsectors + i); - if (nflag == 0 && write(f, (caddr_t)&curbad, sizeof(curbad)) != - sizeof(curbad)) { - char msg[80]; - (void)sprintf(msg, "write bad sector file %d", i/2); - warn("%s", msg); - } - if (badfile != -1) - break; - } - if (nflag == 0 && (dp->d_flags & D_BADSECT) == 0) { - dp->d_flags |= D_BADSECT; - dp->d_checksum = 0; - dp->d_checksum = dkcksum(dp); - if (ioctl(f, DIOCWDINFO, dp) < 0) - err(1, "can't write disklabel to enable bad sector handling"); - } -#ifdef DIOCSBAD - if (nflag == 0 && ioctl(f, DIOCSBAD, (caddr_t)&curbad) < 0) - warnx("can't sync bad-sector file; reboot for changes to take effect"); -#endif - exit(0); -} - -static void -usage() -{ - fprintf(stderr, "%s\n%s\n%s\n", - "usage: bad144 [-f] disk [snum [bn ...]]", - " bad144 -a [-f] [-c] disk bn ...", - " bad144 -s [-v] disk"); - exit(1); -} - -daddr_t -getold(f, bad) - int f; - struct dkbad *bad; -{ - register int i; - daddr_t sn; - char msg[80]; - - if (badfile == -1) - i = 0; - else - i = badfile * 2; - for (; i < 10 && i < dp->d_nsectors; i += 2) { - sn = size - dp->d_nsectors + i; - if (lseek(f, dp->d_secsize * (off_t)sn, SEEK_SET) < 0) - err(4, "lseek"); - if (read(f, (char *) bad, dp->d_secsize) == dp->d_secsize) { - if (i > 0) - printf("Using bad-sector file %d\n", i/2); - return(sn); - } - (void)sprintf(msg, "read bad sector file at sn %d", sn); - warn("%s", msg); - if (badfile != -1) - break; - } - errx(1, "%s: can't read bad block info", name); - /*NOTREACHED*/ -} - -int -checkold(oldbad) - struct dkbad *oldbad; -{ - register int i; - register struct bt_bad *bt; - daddr_t sn, lsn=0; - int errors = 0, warned = 0; - - if (oldbad->bt_flag != DKBAD_MAGIC) { - warnx("%s: bad flag in bad-sector table", name); - errors++; - } - if (oldbad->bt_mbz != 0) { - warnx("%s: bad magic number", name); - errors++; - } - bt = oldbad->bt_bad; - for (i = 0; i < DKBAD_MAXBAD; i++, bt++) { - if (bt->bt_cyl == DKBAD_NOCYL && - bt->bt_trksec == DKBAD_NOTRKSEC) - break; - if ((bt->bt_cyl >= dp->d_ncylinders) || - ((bt->bt_trksec >> 8) >= dp->d_ntracks) || - ((bt->bt_trksec & 0xff) >= dp->d_nsectors)) { - warnx( - "cyl/trk/sect out of range in existing entry: sn=%d, cn=%d, tn=%d, sn=%d", - badsn(bt), bt->bt_cyl, bt->bt_trksec>>8, bt->bt_trksec & 0xff); - errors++; - } - sn = (bt->bt_cyl * dp->d_ntracks + - (bt->bt_trksec >> 8)) * - dp->d_nsectors + (bt->bt_trksec & 0xff); - if (i > 0 && sn < lsn && !warned) { - warnx("bad sector file is out of order"); - errors++; - warned++; - } - if (i > 0 && sn == lsn) { - warnx("bad sector file contains duplicates (sn %d)", sn); - errors++; - } - lsn = sn; - } - if (errors) - exit(1); - return (i); -} - -/* - * Move the bad sector replacements - * to make room for the new bad sectors. - * new is the new number of bad sectors, old is the previous count. - */ -void -shift(f, new, old) - int f, new, old; -{ - daddr_t repl; - - /* - * First replacement is last sector of second-to-last track. - */ - repl = size - dp->d_nsectors - 1; - new--; old--; - while (new >= 0 && new != old) { - if (old < 0 || - compare(&curbad.bt_bad[new], &oldbad.bt_bad[old]) > 0) { - /* - * Insert new replacement here-- copy original - * sector if requested and possible, - * otherwise write a zero block. - */ - if (!copy || - !blkcopy(f, badsn(&curbad.bt_bad[new]), repl - new)) - blkzero(f, repl - new); - } else { - if (blkcopy(f, repl - old, repl - new) == 0) - warnx("can't copy replacement sector %d to %d", - repl-old, repl-new); - old--; - } - new--; - } -} - -/* - * Copy disk sector s1 to s2. - */ -int -blkcopy(f, s1, s2) - int f; - daddr_t s1, s2; -{ - register tries, n; - char *buf; - - buf = alloca((unsigned)dp->d_secsize); - if (buf == (char *)NULL) - errx(20, "alloca failed"); - - for (tries = 0; tries < RETRIES; tries++) { - if (lseek(f, (off_t)dp->d_secsize * s1, SEEK_SET) < 0) - err(4, "lseek"); - if ((n = read(f, buf, dp->d_secsize)) == dp->d_secsize) - break; - } - if (n != dp->d_secsize) { - if (n < 0) - warn("can't read sector, %d", s1); - else - warnx("can't read sector, %d", s1); - return(0); - } - if (lseek(f, (off_t)dp->d_secsize * s2, SEEK_SET) < 0) - err(4, "lseek"); - if (verbose) - printf("copying %d to %d\n", s1, s2); - if (nflag == 0 && write(f, buf, dp->d_secsize) != dp->d_secsize) { - warn("can't write replacement sector, %d", s2); - return(0); - } - return(1); -} - - -void -blkzero(f, sn) - int f; - daddr_t sn; -{ - char *zbuf; - - zbuf = alloca((unsigned)dp->d_secsize); - if (zbuf == (char *)NULL) - errx(20, "alloca failed"); - - memset(zbuf, 0, dp->d_secsize); - - if (lseek(f, (off_t)dp->d_secsize * sn, SEEK_SET) < 0) - err(4, "lseek"); - if (verbose) - printf("zeroing %d\n", sn); - if (nflag == 0 && write(f, zbuf, dp->d_secsize) != dp->d_secsize) - warn("can't write replacement sector, %d", sn); -} - -int -compare(cvb1, cvb2) - const void *cvb1, *cvb2; -{ - const struct bt_bad *b1 = cvb1, *b2 = cvb2; - - if (b1->bt_cyl > b2->bt_cyl) - return(1); - if (b1->bt_cyl < b2->bt_cyl) - return(-1); - if (b1->bt_trksec == b2->bt_trksec) - dups++; - return (b1->bt_trksec - b2->bt_trksec); -} - -daddr_t -badsn(bt) - register struct bt_bad *bt; -{ - return ((bt->bt_cyl*dp->d_ntracks + (bt->bt_trksec>>8)) * dp->d_nsectors - + (bt->bt_trksec&0xff)); -} - |