Annotation of 43BSDReno/usr.sbin/bad144/bad144.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * Copyright (c) 1980,1986,1988 Regents of the University of California.
                      3:  * All rights reserved.
                      4:  *
                      5:  * Redistribution and use in source and binary forms are permitted provided
                      6:  * that: (1) source distributions retain this entire copyright notice and
                      7:  * comment, and (2) distributions including binaries display the following
                      8:  * acknowledgement:  ``This product includes software developed by the
                      9:  * University of California, Berkeley and its contributors'' in the
                     10:  * documentation or other materials provided with the distribution and in
                     11:  * all advertising materials mentioning features or use of this software.
                     12:  * Neither the name of the University nor the names of its contributors may
                     13:  * be used to endorse or promote products derived from this software without
                     14:  * specific prior written permission.
                     15:  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
                     16:  * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
                     17:  * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
                     18:  */
                     19: 
                     20: #ifndef lint
                     21: char copyright[] =
                     22: "@(#) Copyright (c) 1980,1986,1988 Regents of the University of California.\n\
                     23:  All rights reserved.\n";
                     24: #endif not lint
                     25: 
                     26: #ifndef lint
                     27: static char sccsid[] = "@(#)bad144.c   5.18 (Berkeley) 6/1/90";
                     28: #endif not lint
                     29: 
                     30: /*
                     31:  * bad144
                     32:  *
                     33:  * This program prints and/or initializes a bad block record for a pack,
                     34:  * in the format used by the DEC standard 144.
                     35:  * It can also add bad sector(s) to the record, moving the sector
                     36:  * replacements as necessary.
                     37:  *
                     38:  * It is preferable to write the bad information with a standard formatter,
                     39:  * but this program will do.
                     40:  * 
                     41:  * RP06 sectors are marked as bad by inverting the format bit in the
                     42:  * header; on other drives the valid-sector bit is cleared.
                     43:  */
                     44: #include <sys/param.h>
                     45: #include <sys/dkbad.h>
                     46: #include <sys/ioctl.h>
                     47: #include <ufs/fs.h>
                     48: #include <sys/file.h>
                     49: #include <sys/disklabel.h>
                     50: 
                     51: #include <stdio.h>
                     52: #include <paths.h>
                     53: 
                     54: #define RETRIES        10              /* number of retries on reading old sectors */
                     55: #define        RAWPART "c"             /* disk partition containing badsector tables */
                     56: 
                     57: int    fflag, add, copy, verbose, nflag;
                     58: int    compare();
                     59: int    dups;
                     60: int    badfile = -1;           /* copy of badsector table to use, -1 if any */
                     61: #define MAXSECSIZE     1024
                     62: struct dkbad curbad, oldbad;
                     63: #define        DKBAD_MAGIC     0
                     64: 
                     65: char   label[BBSIZE];
                     66: daddr_t        size, getold(), badsn();
                     67: struct disklabel *dp;
                     68: char   name[BUFSIZ];
                     69: char   *malloc();
                     70: off_t  lseek();
                     71: 
                     72: main(argc, argv)
                     73:        int argc;
                     74:        char *argv[];
                     75: {
                     76:        register struct bt_bad *bt;
                     77:        daddr_t sn, bn[126];
                     78:        int i, f, nbad, new, bad, errs;
                     79: 
                     80:        argc--, argv++;
                     81:        while (argc > 0 && **argv == '-') {
                     82:                (*argv)++;
                     83:                while (**argv) {
                     84:                        switch (**argv) {
                     85: #if vax
                     86:                            case 'f':
                     87:                                fflag++;
                     88:                                break;
                     89: #endif
                     90:                            case 'a':
                     91:                                add++;
                     92:                                break;
                     93:                            case 'c':
                     94:                                copy++;
                     95:                                break;
                     96:                            case 'v':
                     97:                                verbose++;
                     98:                                break;
                     99:                            case 'n':
                    100:                                nflag++;
                    101:                                verbose++;
                    102:                                break;
                    103:                            default:
                    104:                                if (**argv >= '0' && **argv <= '4') {
                    105:                                        badfile = **argv - '0';
                    106:                                        break;
                    107:                                }
                    108:                                goto usage;
                    109:                        }
                    110:                        (*argv)++;
                    111:                }
                    112:                argc--, argv++;
                    113:        }
                    114:        if (argc < 1) {
                    115: usage:
                    116:                fprintf(stderr,
                    117:                  "usage: bad144 [ -f ] disk [ snum [ bn ... ] ]\n");
                    118:                fprintf(stderr,
                    119:              "to read or overwrite bad-sector table, e.g.: bad144 hp0\n");
                    120:                fprintf(stderr,
                    121:                  "or bad144 -a [ -f ] [ -c ] disk  bn ...\n");
                    122:                fprintf(stderr, "where options are:\n");
                    123:                fprintf(stderr, "\t-a  add new bad sectors to the table\n");
                    124:                fprintf(stderr, "\t-f  reformat listed sectors as bad\n");
                    125:                fprintf(stderr, "\t-c  copy original sector to replacement\n");
                    126:                exit(1);
                    127:        }
                    128:        if (argv[0][0] != '/')
                    129:                (void)sprintf(name, "%s/r%s%s", _PATH_DEV, argv[0], RAWPART);
                    130:        else
                    131:                strcpy(name, argv[0]);
                    132:        f = open(name, argc == 1? O_RDONLY : O_RDWR);
                    133:        if (f < 0)
                    134:                Perror(name);
                    135:        if (read(f, label, sizeof(label)) < 0) 
                    136:                Perror("read");
                    137:        for (dp = (struct disklabel *)(label + LABELOFFSET);
                    138:            dp < (struct disklabel *)
                    139:                (label + sizeof(label) - sizeof(struct disklabel));
                    140:            dp = (struct disklabel *)((char *)dp + 64))
                    141:                if (dp->d_magic == DISKMAGIC && dp->d_magic2 == DISKMAGIC)
                    142:                        break;
                    143:        if (dp->d_magic != DISKMAGIC || dp->d_magic2 != DISKMAGIC) {
                    144:                fprintf(stderr, "Bad pack magic number (pack is unlabeled)\n");
                    145:                exit(1);
                    146:        }
                    147:        if (dp->d_secsize > MAXSECSIZE || dp->d_secsize <= 0) {
                    148:                fprintf(stderr, "Disk sector size too large/small (%d)\n",
                    149:                        dp->d_secsize);
                    150:                exit(7);
                    151:        }
                    152:        size = dp->d_nsectors * dp->d_ntracks * dp->d_ncylinders; 
                    153:        argc--;
                    154:        argv++;
                    155:        if (argc == 0) {
                    156:                sn = getold(f, &oldbad);
                    157:                printf("bad block information at sector %d in %s:\n",
                    158:                    sn, name);
                    159:                printf("cartridge serial number: %d(10)\n", oldbad.bt_csn);
                    160:                switch (oldbad.bt_flag) {
                    161: 
                    162:                case (u_short)-1:
                    163:                        printf("alignment cartridge\n");
                    164:                        break;
                    165: 
                    166:                case DKBAD_MAGIC:
                    167:                        break;
                    168: 
                    169:                default:
                    170:                        printf("bt_flag=%x(16)?\n", oldbad.bt_flag);
                    171:                        break;
                    172:                }
                    173:                bt = oldbad.bt_bad;
                    174:                for (i = 0; i < 126; i++) {
                    175:                        bad = (bt->bt_cyl<<16) + bt->bt_trksec;
                    176:                        if (bad < 0)
                    177:                                break;
                    178:                        printf("sn=%d, cn=%d, tn=%d, sn=%d\n", badsn(bt),
                    179:                            bt->bt_cyl, bt->bt_trksec>>8, bt->bt_trksec&0xff);
                    180:                        bt++;
                    181:                }
                    182:                (void) checkold(&oldbad);
                    183:                exit(0);
                    184:        }
                    185:        if (add) {
                    186:                /*
                    187:                 * Read in the old badsector table.
                    188:                 * Verify that it makes sense, and the bad sectors
                    189:                 * are in order.  Copy the old table to the new one.
                    190:                 */
                    191:                (void) getold(f, &oldbad);
                    192:                i = checkold(&oldbad);
                    193:                if (verbose)
                    194:                        printf("Had %d bad sectors, adding %d\n", i, argc);
                    195:                if (i + argc > 126) {
                    196:                        printf("bad144: not enough room for %d more sectors\n",
                    197:                                argc);
                    198:                        printf("limited to 126 by information format\n");
                    199:                        exit(1);
                    200:                }
                    201:                curbad = oldbad;
                    202:        } else {
                    203:                curbad.bt_csn = atoi(*argv++);
                    204:                argc--;
                    205:                curbad.bt_mbz = 0;
                    206:                curbad.bt_flag = DKBAD_MAGIC;
                    207:                if (argc > 126) {
                    208:                        printf("bad144: too many bad sectors specified\n");
                    209:                        printf("limited to 126 by information format\n");
                    210:                        exit(1);
                    211:                }
                    212:                i = 0;
                    213:        }
                    214:        errs = 0;
                    215:        new = argc;
                    216:        while (argc > 0) {
                    217:                daddr_t sn = atoi(*argv++);
                    218:                argc--;
                    219:                if (sn < 0 || sn >= size) {
                    220:                        printf("%d: out of range [0,%d) for disk %s\n",
                    221:                            sn, size, dp->d_typename);
                    222:                        errs++;
                    223:                        continue;
                    224:                }
                    225:                bn[i] = sn;
                    226:                curbad.bt_bad[i].bt_cyl = sn / (dp->d_nsectors*dp->d_ntracks);
                    227:                sn %= (dp->d_nsectors*dp->d_ntracks);
                    228:                curbad.bt_bad[i].bt_trksec =
                    229:                    ((sn/dp->d_nsectors) << 8) + (sn%dp->d_nsectors);
                    230:                i++;
                    231:        }
                    232:        if (errs)
                    233:                exit(1);
                    234:        nbad = i;
                    235:        while (i < 126) {
                    236:                curbad.bt_bad[i].bt_trksec = -1;
                    237:                curbad.bt_bad[i].bt_cyl = -1;
                    238:                i++;
                    239:        }
                    240:        if (add) {
                    241:                /*
                    242:                 * Sort the new bad sectors into the list.
                    243:                 * Then shuffle the replacement sectors so that
                    244:                 * the previous bad sectors get the same replacement data.
                    245:                 */
                    246:                qsort((char *)curbad.bt_bad, nbad, sizeof (struct bt_bad),
                    247:                    compare);
                    248:                if (dups) {
                    249:                        fprintf(stderr,
                    250: "bad144: bad sectors have been duplicated; can't add existing sectors\n");
                    251:                        exit(3);
                    252:                }
                    253:                shift(f, nbad, nbad-new);
                    254:        }
                    255:        if (badfile == -1)
                    256:                i = 0;
                    257:        else
                    258:                i = badfile * 2;
                    259:        for (; i < 10 && i < dp->d_nsectors; i += 2) {
                    260:                if (lseek(f, dp->d_secsize * (size - dp->d_nsectors + i),
                    261:                    L_SET) < 0)
                    262:                        Perror("lseek");
                    263:                if (verbose)
                    264:                        printf("write badsect file at %d\n",
                    265:                                size - dp->d_nsectors + i);
                    266:                if (nflag == 0 && write(f, (caddr_t)&curbad, sizeof(curbad)) !=
                    267:                    sizeof(curbad)) {
                    268:                        char msg[80];
                    269:                        (void)sprintf(msg, "bad144: write bad sector file %d",
                    270:                            i/2);
                    271:                        perror(msg);
                    272:                }
                    273:                if (badfile != -1)
                    274:                        break;
                    275:        }
                    276: #ifdef vax
                    277:        if (nflag == 0 && fflag)
                    278:                for (i = nbad - new; i < nbad; i++)
                    279:                        format(f, bn[i]);
                    280: #endif
                    281: #ifdef DIOCSBAD
                    282:        if (nflag == 0 && ioctl(f, DIOCSBAD, (caddr_t)&curbad) < 0)
                    283:                fprintf(stderr,
                    284:        "Can't sync bad-sector file; reboot for changes to take effect\n");
                    285: #endif
                    286:        exit(0);
                    287: }
                    288: 
                    289: daddr_t
                    290: getold(f, bad)
                    291: struct dkbad *bad;
                    292: {
                    293:        register int i;
                    294:        daddr_t sn;
                    295:        char msg[80];
                    296: 
                    297:        if (badfile == -1)
                    298:                i = 0;
                    299:        else
                    300:                i = badfile * 2;
                    301:        for (; i < 10 && i < dp->d_nsectors; i += 2) {
                    302:                sn = size - dp->d_nsectors + i;
                    303:                if (lseek(f, sn * dp->d_secsize, L_SET) < 0)
                    304:                        Perror("lseek");
                    305:                if (read(f, (char *) bad, dp->d_secsize) == dp->d_secsize) {
                    306:                        if (i > 0)
                    307:                                printf("Using bad-sector file %d\n", i/2);
                    308:                        return(sn);
                    309:                }
                    310:                (void)sprintf(msg, "bad144: read bad sector file at sn %d", sn);
                    311:                perror(msg);
                    312:                if (badfile != -1)
                    313:                        break;
                    314:        }
                    315:        fprintf(stderr, "bad144: %s: can't read bad block info\n", name);
                    316:        exit(1);
                    317:        /*NOTREACHED*/
                    318: }
                    319: 
                    320: checkold()
                    321: {
                    322:        register int i;
                    323:        register struct bt_bad *bt;
                    324:        daddr_t sn, lsn;
                    325:        int errors = 0, warned = 0;
                    326: 
                    327:        if (oldbad.bt_flag != DKBAD_MAGIC) {
                    328:                fprintf(stderr, "bad144: %s: bad flag in bad-sector table\n",
                    329:                        name);
                    330:                errors++;
                    331:        }
                    332:        if (oldbad.bt_mbz != 0) {
                    333:                fprintf(stderr, "bad144: %s: bad magic number\n", name);
                    334:                errors++;
                    335:        }
                    336:        bt = oldbad.bt_bad;
                    337:        for (i = 0; i < 126; i++, bt++) {
                    338:                if (bt->bt_cyl == 0xffff && bt->bt_trksec == 0xffff)
                    339:                        break;
                    340:                if ((bt->bt_cyl >= dp->d_ncylinders) ||
                    341:                    ((bt->bt_trksec >> 8) >= dp->d_ntracks) ||
                    342:                    ((bt->bt_trksec & 0xff) >= dp->d_nsectors)) {
                    343:                        fprintf(stderr,
                    344:                     "bad144: cyl/trk/sect out of range in existing entry: ");
                    345:                        fprintf(stderr, "sn=%d, cn=%d, tn=%d, sn=%d\n",
                    346:                                badsn(bt), bt->bt_cyl, bt->bt_trksec>>8,
                    347:                                bt->bt_trksec & 0xff);
                    348:                        errors++;
                    349:                }
                    350:                sn = (bt->bt_cyl * dp->d_ntracks +
                    351:                    (bt->bt_trksec >> 8)) *
                    352:                    dp->d_nsectors + (bt->bt_trksec & 0xff);
                    353:                if (i > 0 && sn < lsn && !warned) {
                    354:                    fprintf(stderr,
                    355:                        "bad144: bad sector file is out of order\n");
                    356:                    errors++;
                    357:                    warned++;
                    358:                }
                    359:                if (i > 0 && sn == lsn) {
                    360:                    fprintf(stderr,
                    361:                        "bad144: bad sector file contains duplicates (sn %d)\n",
                    362:                        sn);
                    363:                    errors++;
                    364:                }
                    365:                lsn = sn;
                    366:        }
                    367:        if (errors)
                    368:                exit(1);
                    369:        return (i);
                    370: }
                    371: 
                    372: /*
                    373:  * Move the bad sector replacements
                    374:  * to make room for the new bad sectors.
                    375:  * new is the new number of bad sectors, old is the previous count.
                    376:  */
                    377: shift(f, new, old)
                    378: {
                    379:        daddr_t repl;
                    380: 
                    381:        /*
                    382:         * First replacement is last sector of second-to-last track.
                    383:         */
                    384:        repl = size - dp->d_nsectors - 1;
                    385:        new--; old--;
                    386:        while (new >= 0 && new != old) {
                    387:                if (old < 0 ||
                    388:                    compare(&curbad.bt_bad[new], &oldbad.bt_bad[old]) > 0) {
                    389:                        /*
                    390:                         * Insert new replacement here-- copy original
                    391:                         * sector if requested and possible,
                    392:                         * otherwise write a zero block.
                    393:                         */
                    394:                        if (!copy ||
                    395:                            !blkcopy(f, badsn(&curbad.bt_bad[new]), repl - new))
                    396:                                blkzero(f, repl - new);
                    397:                } else {
                    398:                        if (blkcopy(f, repl - old, repl - new) == 0)
                    399:                            fprintf(stderr,
                    400:                                "Can't copy replacement sector %d to %d\n",
                    401:                                repl-old, repl-new);
                    402:                        old--;
                    403:                }
                    404:                new--;
                    405:        }
                    406: }
                    407: 
                    408: char *buf;
                    409: 
                    410: /*
                    411:  *  Copy disk sector s1 to s2.
                    412:  */
                    413: blkcopy(f, s1, s2)
                    414: daddr_t s1, s2;
                    415: {
                    416:        register tries, n;
                    417: 
                    418:        if (buf == (char *)NULL) {
                    419:                buf = malloc((unsigned)dp->d_secsize);
                    420:                if (buf == (char *)NULL) {
                    421:                        fprintf(stderr, "Out of memory\n");
                    422:                        exit(20);
                    423:                }
                    424:        }
                    425:        for (tries = 0; tries < RETRIES; tries++) {
                    426:                if (lseek(f, dp->d_secsize * s1, L_SET) < 0)
                    427:                        Perror("lseek");
                    428:                if ((n = read(f, buf, dp->d_secsize)) == dp->d_secsize)
                    429:                        break;
                    430:        }
                    431:        if (n != dp->d_secsize) {
                    432:                fprintf(stderr, "bad144: can't read sector, %d: ", s1);
                    433:                if (n < 0)
                    434:                        perror((char *)0);
                    435:                return(0);
                    436:        }
                    437:        if (lseek(f, dp->d_secsize * s2, L_SET) < 0)
                    438:                Perror("lseek");
                    439:        if (verbose)
                    440:                printf("copying %d to %d\n", s1, s2);
                    441:        if (nflag == 0 && write(f, buf, dp->d_secsize) != dp->d_secsize) {
                    442:                fprintf(stderr,
                    443:                    "bad144: can't write replacement sector, %d: ", s2);
                    444:                perror((char *)0);
                    445:                return(0);
                    446:        }
                    447:        return(1);
                    448: }
                    449: 
                    450: char *zbuf;
                    451: 
                    452: blkzero(f, sn)
                    453: daddr_t sn;
                    454: {
                    455: 
                    456:        if (zbuf == (char *)NULL) {
                    457:                zbuf = malloc((unsigned)dp->d_secsize);
                    458:                if (zbuf == (char *)NULL) {
                    459:                        fprintf(stderr, "Out of memory\n");
                    460:                        exit(20);
                    461:                }
                    462:        }
                    463:        if (lseek(f, dp->d_secsize * sn, L_SET) < 0)
                    464:                Perror("lseek");
                    465:        if (verbose)
                    466:                printf("zeroing %d\n", sn);
                    467:        if (nflag == 0 && write(f, zbuf, dp->d_secsize) != dp->d_secsize) {
                    468:                fprintf(stderr,
                    469:                    "bad144: can't write replacement sector, %d: ", sn);
                    470:                perror((char *)0);
                    471:        }
                    472: }
                    473: 
                    474: compare(b1, b2)
                    475: register struct bt_bad *b1, *b2;
                    476: {
                    477:        if (b1->bt_cyl > b2->bt_cyl)
                    478:                return(1);
                    479:        if (b1->bt_cyl < b2->bt_cyl)
                    480:                return(-1);
                    481:        if (b1->bt_trksec == b2->bt_trksec)
                    482:                dups++;
                    483:        return (b1->bt_trksec - b2->bt_trksec);
                    484: }
                    485: 
                    486: daddr_t
                    487: badsn(bt)
                    488: register struct bt_bad *bt;
                    489: {
                    490:        return ((bt->bt_cyl*dp->d_ntracks + (bt->bt_trksec>>8)) * dp->d_nsectors
                    491:                + (bt->bt_trksec&0xff));
                    492: }
                    493: 
                    494: #ifdef vax
                    495: #include <machine/dkio.h>
                    496: 
                    497: struct rp06hdr {
                    498:        short   h_cyl;
                    499:        short   h_trksec;
                    500:        short   h_key1;
                    501:        short   h_key2;
                    502:        char    h_data[512];
                    503: #define        RP06_FMT        010000          /* 1 == 16 bit, 0 == 18 bit */
                    504: };
                    505: 
                    506: /*
                    507:  * Most massbus and unibus drives
                    508:  * have headers of this form
                    509:  */
                    510: struct hpuphdr {
                    511:        u_short hpup_cyl;
                    512:        u_char  hpup_sect;
                    513:        u_char  hpup_track;
                    514:        char    hpup_data[512];
                    515: #define        HPUP_OKSECT     0xc000          /* this normally means sector is good */
                    516: #define        HPUP_16BIT      0x1000          /* 1 == 16 bit format */
                    517: };
                    518: int rp06format(), hpupformat();
                    519: 
                    520: struct formats {
                    521:        char    *f_name;                /* disk name */
                    522:        int     f_bufsize;              /* size of sector + header */
                    523:        int     f_bic;                  /* value to bic in hpup_cyl */
                    524:        int     (*f_routine)();         /* routine for special handling */
                    525: } formats[] = {
                    526:        { "rp06",       sizeof (struct rp06hdr), RP06_FMT,      rp06format },
                    527:        { "eagle",      sizeof (struct hpuphdr), HPUP_OKSECT,   hpupformat },
                    528:        { "capricorn",  sizeof (struct hpuphdr), HPUP_OKSECT,   hpupformat },
                    529:        { "rm03",       sizeof (struct hpuphdr), HPUP_OKSECT,   hpupformat },
                    530:        { "rm05",       sizeof (struct hpuphdr), HPUP_OKSECT,   hpupformat },
                    531:        { "9300",       sizeof (struct hpuphdr), HPUP_OKSECT,   hpupformat },
                    532:        { "9766",       sizeof (struct hpuphdr), HPUP_OKSECT,   hpupformat },
                    533:        { 0, 0, 0, 0 }
                    534: };
                    535: 
                    536: /*ARGSUSED*/
                    537: hpupformat(fp, dp, blk, buf, count)
                    538:        struct formats *fp;
                    539:        struct disklabel *dp;
                    540:        daddr_t blk;
                    541:        char *buf;
                    542:        int count;
                    543: {
                    544:        struct hpuphdr *hdr = (struct hpuphdr *)buf;
                    545:        int sect;
                    546: 
                    547:        if (count < sizeof(struct hpuphdr)) {
                    548:                hdr->hpup_cyl = (HPUP_OKSECT | HPUP_16BIT) |
                    549:                        (blk / (dp->d_nsectors * dp->d_ntracks));
                    550:                sect = blk % (dp->d_nsectors * dp->d_ntracks);
                    551:                hdr->hpup_track = (u_char)(sect / dp->d_nsectors);
                    552:                hdr->hpup_sect = (u_char)(sect % dp->d_nsectors);
                    553:        }
                    554:        return (0);
                    555: }
                    556: 
                    557: /*ARGSUSED*/
                    558: rp06format(fp, dp, blk, buf, count)
                    559:        struct formats *fp;
                    560:        struct disklabel *dp;
                    561:        daddr_t blk;
                    562:        char *buf;
                    563:        int count;
                    564: {
                    565: 
                    566:        if (count < sizeof(struct rp06hdr)) {
                    567:                fprintf(stderr, "Can't read header on blk %d, can't reformat\n",
                    568:                        blk);
                    569:                return (-1);
                    570:        }
                    571:        return (0);
                    572: }
                    573: 
                    574: format(fd, blk)
                    575:        int fd;
                    576:        daddr_t blk;
                    577: {
                    578:        register struct formats *fp;
                    579:        static char *buf;
                    580:        static char bufsize;
                    581:        struct format_op fop;
                    582:        int n;
                    583: 
                    584:        for (fp = formats; fp->f_name; fp++)
                    585:                if (strcmp(dp->d_typename, fp->f_name) == 0)
                    586:                        break;
                    587:        if (fp->f_name == 0) {
                    588:                fprintf(stderr, "bad144: don't know how to format %s disks\n",
                    589:                        dp->d_typename);
                    590:                exit(2);
                    591:        }
                    592:        if (buf && bufsize < fp->f_bufsize) {
                    593:                free(buf);
                    594:                buf = NULL;
                    595:        }
                    596:        if (buf == NULL)
                    597:                buf = malloc((unsigned)fp->f_bufsize);
                    598:        if (buf == NULL) {
                    599:                fprintf(stderr, "bad144: can't allocate sector buffer\n");
                    600:                exit(3);
                    601:        }
                    602:        bufsize = fp->f_bufsize;
                    603:        /*
                    604:         * Here we do the actual formatting.  All we really
                    605:         * do is rewrite the sector header and flag the bad sector
                    606:         * according to the format table description.  If a special
                    607:         * purpose format routine is specified, we allow it to
                    608:         * process the sector as well.
                    609:         */
                    610:        if (verbose)
                    611:                printf("format blk %d\n", blk);
                    612:        bzero((char *)&fop, sizeof(fop));
                    613:        fop.df_buf = buf;
                    614:        fop.df_count = fp->f_bufsize;
                    615:        fop.df_startblk = blk;
                    616:        bzero(buf, fp->f_bufsize);
                    617:        if (ioctl(fd, DIOCRFORMAT, &fop) < 0)
                    618:                perror("bad144: read format");
                    619:        if (fp->f_routine &&
                    620:            (*fp->f_routine)(fp, dp, blk, buf, fop.df_count) != 0)
                    621:                return;
                    622:        if (fp->f_bic) {
                    623:                struct hpuphdr *xp = (struct hpuphdr *)buf;
                    624: 
                    625:                xp->hpup_cyl &= ~fp->f_bic;
                    626:        }
                    627:        if (nflag)
                    628:                return;
                    629:        bzero((char *)&fop, sizeof(fop));
                    630:        fop.df_buf = buf;
                    631:        fop.df_count = fp->f_bufsize;
                    632:        fop.df_startblk = blk;
                    633:        if (ioctl(fd, DIOCWFORMAT, &fop) < 0)
                    634:                Perror("write format");
                    635:        if (fop.df_count != fp->f_bufsize) {
                    636:                char msg[80];
                    637:                (void)sprintf(msg, "bad144: write format %d", blk);
                    638:                perror(msg);
                    639:        }
                    640: }
                    641: #endif
                    642: 
                    643: Perror(op)
                    644:        char *op;
                    645: {
                    646: 
                    647:        fprintf(stderr, "bad144: "); perror(op);
                    648:        exit(4);
                    649: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.