1*51151Sbostic /* 2*51151Sbostic * Copyright (c) 1983, 1989 The Regents of the University of California. 3*51151Sbostic * All rights reserved. 4*51151Sbostic * 5*51151Sbostic * Redistribution and use in source and binary forms, with or without 6*51151Sbostic * modification, are permitted provided that the following conditions 7*51151Sbostic * are met: 8*51151Sbostic * 1. Redistributions of source code must retain the above copyright 9*51151Sbostic * notice, this list of conditions and the following disclaimer. 10*51151Sbostic * 2. Redistributions in binary form must reproduce the above copyright 11*51151Sbostic * notice, this list of conditions and the following disclaimer in the 12*51151Sbostic * documentation and/or other materials provided with the distribution. 13*51151Sbostic * 3. All advertising materials mentioning features or use of this software 14*51151Sbostic * must display the following acknowledgement: 15*51151Sbostic * This product includes software developed by the University of 16*51151Sbostic * California, Berkeley and its contributors. 17*51151Sbostic * 4. Neither the name of the University nor the names of its contributors 18*51151Sbostic * may be used to endorse or promote products derived from this software 19*51151Sbostic * without specific prior written permission. 20*51151Sbostic * 21*51151Sbostic * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 22*51151Sbostic * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 23*51151Sbostic * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 24*51151Sbostic * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 25*51151Sbostic * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 26*51151Sbostic * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 27*51151Sbostic * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 28*51151Sbostic * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 29*51151Sbostic * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 30*51151Sbostic * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 31*51151Sbostic * SUCH DAMAGE. 32*51151Sbostic */ 33*51151Sbostic 34*51151Sbostic #ifndef lint 35*51151Sbostic static char sccsid[] = "@(#)newfs.c 6.28 (Berkeley) 8/6/91"; 36*51151Sbostic #endif /* not lint */ 37*51151Sbostic 38*51151Sbostic #ifndef lint 39*51151Sbostic char copyright[] = 40*51151Sbostic "@(#) Copyright (c) 1983, 1989 Regents of the University of California.\n\ 41*51151Sbostic All rights reserved.\n"; 42*51151Sbostic #endif /* not lint */ 43*51151Sbostic 44*51151Sbostic /* 45*51151Sbostic * newfs: friendly front end to mkfs 46*51151Sbostic */ 47*51151Sbostic #include <sys/param.h> 48*51151Sbostic #include <sys/stat.h> 49*51151Sbostic #include <ufs/fs.h> 50*51151Sbostic #include <ufs/dir.h> 51*51151Sbostic #include <ufs/dinode.h> 52*51151Sbostic #include <sys/ioctl.h> 53*51151Sbostic #include <sys/disklabel.h> 54*51151Sbostic #include <sys/file.h> 55*51151Sbostic #include <sys/mount.h> 56*51151Sbostic 57*51151Sbostic #include <errno.h> 58*51151Sbostic #include <unistd.h> 59*51151Sbostic #include <stdio.h> 60*51151Sbostic #include <stdlib.h> 61*51151Sbostic #include <ctype.h> 62*51151Sbostic #include <string.h> 63*51151Sbostic #include <paths.h> 64*51151Sbostic #include "config.h" 65*51151Sbostic #include "extern.h" 66*51151Sbostic 67*51151Sbostic #define COMPAT /* allow non-labeled disks */ 68*51151Sbostic 69*51151Sbostic int mfs; /* run as the memory based filesystem */ 70*51151Sbostic int Nflag; /* run without writing file system */ 71*51151Sbostic int fssize; /* file system size */ 72*51151Sbostic int ntracks; /* # tracks/cylinder */ 73*51151Sbostic int nsectors; /* # sectors/track */ 74*51151Sbostic int nphyssectors; /* # sectors/track including spares */ 75*51151Sbostic int secpercyl; /* sectors per cylinder */ 76*51151Sbostic int trackspares = -1; /* spare sectors per track */ 77*51151Sbostic int cylspares = -1; /* spare sectors per cylinder */ 78*51151Sbostic int sectorsize; /* bytes/sector */ 79*51151Sbostic #ifdef tahoe 80*51151Sbostic int realsectorsize; /* bytes/sector in hardware */ 81*51151Sbostic #endif 82*51151Sbostic int rpm; /* revolutions/minute of drive */ 83*51151Sbostic int interleave; /* hardware sector interleave */ 84*51151Sbostic int trackskew = -1; /* sector 0 skew, per track */ 85*51151Sbostic int headswitch; /* head switch time, usec */ 86*51151Sbostic int trackseek; /* track-to-track seek, usec */ 87*51151Sbostic int fsize = 0; /* fragment size */ 88*51151Sbostic int bsize = 0; /* block size */ 89*51151Sbostic int cpg = DESCPG; /* cylinders/cylinder group */ 90*51151Sbostic int cpgflg; /* cylinders/cylinder group flag was given */ 91*51151Sbostic int minfree = MINFREE; /* free space threshold */ 92*51151Sbostic int opt = DEFAULTOPT; /* optimization preference (space or time) */ 93*51151Sbostic int density; /* number of bytes per inode */ 94*51151Sbostic int maxcontig = MAXCONTIG; /* max contiguous blocks to allocate */ 95*51151Sbostic int rotdelay = ROTDELAY; /* rotational delay between blocks */ 96*51151Sbostic int maxbpg; /* maximum blocks per file in a cyl group */ 97*51151Sbostic int nrpos = NRPOS; /* # of distinguished rotational positions */ 98*51151Sbostic int bbsize = BBSIZE; /* boot block size */ 99*51151Sbostic int sbsize = SBSIZE; /* superblock size */ 100*51151Sbostic int mntflags; /* flags to be passed to mount */ 101*51151Sbostic u_long memleft; /* virtual memory available */ 102*51151Sbostic caddr_t membase; /* start address of memory based filesystem */ 103*51151Sbostic #ifdef COMPAT 104*51151Sbostic char *disktype; 105*51151Sbostic int unlabeled; 106*51151Sbostic #endif 107*51151Sbostic 108*51151Sbostic char device[MAXPATHLEN]; 109*51151Sbostic char *progname, *special; 110*51151Sbostic 111*51151Sbostic static struct disklabel *getdisklabel __P((char *, int)); 112*51151Sbostic static struct disklabel *debug_readlabel __P((int)); 113*51151Sbostic static void rewritelabel __P((char *, int, struct disklabel *)); 114*51151Sbostic static void usage __P((void)); 115*51151Sbostic 116*51151Sbostic int 117*51151Sbostic main(argc, argv) 118*51151Sbostic int argc; 119*51151Sbostic char *argv[]; 120*51151Sbostic { 121*51151Sbostic register int ch; 122*51151Sbostic register struct partition *pp; 123*51151Sbostic register struct disklabel *lp; 124*51151Sbostic struct partition oldpartition; 125*51151Sbostic struct stat st; 126*51151Sbostic int debug, lfs, fsi, fso, segsize; 127*51151Sbostic char *cp, *opstring; 128*51151Sbostic 129*51151Sbostic if (progname = rindex(*argv, '/')) 130*51151Sbostic ++progname; 131*51151Sbostic else 132*51151Sbostic progname = *argv; 133*51151Sbostic 134*51151Sbostic if (strstr(progname, "mfs")) { 135*51151Sbostic mfs = 1; 136*51151Sbostic Nflag++; 137*51151Sbostic } 138*51151Sbostic 139*51151Sbostic /* -F is mfs only and MUST come first! */ 140*51151Sbostic opstring = "F:B:DLNS:T:a:b:c:d:e:f:i:k:l:m:n:o:p:r:s:t:u:x:"; 141*51151Sbostic if (!mfs) 142*51151Sbostic opstring += 2; 143*51151Sbostic 144*51151Sbostic debug = lfs = segsize = 0; 145*51151Sbostic while ((ch = getopt(argc, argv, opstring)) != EOF) 146*51151Sbostic switch(ch) { 147*51151Sbostic case 'B': /* LFS segment size */ 148*51151Sbostic if ((segsize = atoi(optarg)) < LFS_MINSEGSIZE) 149*51151Sbostic fatal("%s: bad segment size", optarg); 150*51151Sbostic break; 151*51151Sbostic case 'D': 152*51151Sbostic debug = 1; 153*51151Sbostic break; 154*51151Sbostic case 'F': 155*51151Sbostic if ((mntflags = atoi(optarg)) == 0) 156*51151Sbostic fatal("%s: bad mount flags", optarg); 157*51151Sbostic break; 158*51151Sbostic case 'L': /* Create lfs */ 159*51151Sbostic lfs = 1; 160*51151Sbostic break; 161*51151Sbostic case 'N': 162*51151Sbostic Nflag++; 163*51151Sbostic break; 164*51151Sbostic case 'S': 165*51151Sbostic if ((sectorsize = atoi(optarg)) <= 0) 166*51151Sbostic fatal("%s: bad sector size", optarg); 167*51151Sbostic break; 168*51151Sbostic #ifdef COMPAT 169*51151Sbostic case 'T': 170*51151Sbostic disktype = optarg; 171*51151Sbostic break; 172*51151Sbostic #endif 173*51151Sbostic case 'a': 174*51151Sbostic if ((maxcontig = atoi(optarg)) <= 0) 175*51151Sbostic fatal("%s: bad max contiguous blocks\n", 176*51151Sbostic optarg); 177*51151Sbostic break; 178*51151Sbostic case 'b': /* used for LFS */ 179*51151Sbostic if ((bsize = atoi(optarg)) < MINBSIZE) 180*51151Sbostic fatal("%s: bad block size", optarg); 181*51151Sbostic break; 182*51151Sbostic case 'c': 183*51151Sbostic if ((cpg = atoi(optarg)) <= 0) 184*51151Sbostic fatal("%s: bad cylinders/group", optarg); 185*51151Sbostic cpgflg++; 186*51151Sbostic break; 187*51151Sbostic case 'd': 188*51151Sbostic if ((rotdelay = atoi(optarg)) < 0) 189*51151Sbostic fatal("%s: bad rotational delay\n", optarg); 190*51151Sbostic break; 191*51151Sbostic case 'e': 192*51151Sbostic if ((maxbpg = atoi(optarg)) <= 0) 193*51151Sbostic fatal("%s: bad blocks per file in a cyl group\n", 194*51151Sbostic optarg); 195*51151Sbostic break; 196*51151Sbostic case 'f': 197*51151Sbostic if ((fsize = atoi(optarg)) <= 0) 198*51151Sbostic fatal("%s: bad frag size", optarg); 199*51151Sbostic break; 200*51151Sbostic case 'i': 201*51151Sbostic if ((density = atoi(optarg)) <= 0) 202*51151Sbostic fatal("%s: bad bytes per inode\n", optarg); 203*51151Sbostic break; 204*51151Sbostic case 'k': 205*51151Sbostic if ((trackskew = atoi(optarg)) < 0) 206*51151Sbostic fatal("%s: bad track skew", optarg); 207*51151Sbostic break; 208*51151Sbostic case 'l': 209*51151Sbostic if ((interleave = atoi(optarg)) <= 0) 210*51151Sbostic fatal("%s: bad interleave", optarg); 211*51151Sbostic break; 212*51151Sbostic case 'm': /* used for LFS */ 213*51151Sbostic if ((minfree = atoi(optarg)) < 0 || minfree > 99) 214*51151Sbostic fatal("%s: bad free space %%\n", optarg); 215*51151Sbostic break; 216*51151Sbostic case 'n': 217*51151Sbostic if ((nrpos = atoi(optarg)) <= 0) 218*51151Sbostic fatal("%s: bad rotational layout count\n", 219*51151Sbostic optarg); 220*51151Sbostic break; 221*51151Sbostic case 'o': 222*51151Sbostic if (strcmp(optarg, "space") == 0) 223*51151Sbostic opt = FS_OPTSPACE; 224*51151Sbostic else if (strcmp(optarg, "time") == 0) 225*51151Sbostic opt = FS_OPTTIME; 226*51151Sbostic else 227*51151Sbostic fatal("%s: bad optimization preference %s", 228*51151Sbostic optarg, "(options are `space' or `time')"); 229*51151Sbostic break; 230*51151Sbostic case 'p': 231*51151Sbostic if ((trackspares = atoi(optarg)) < 0) 232*51151Sbostic fatal("%s: bad spare sectors per track", 233*51151Sbostic optarg); 234*51151Sbostic break; 235*51151Sbostic case 'r': 236*51151Sbostic if ((rpm = atoi(optarg)) <= 0) 237*51151Sbostic fatal("%s: bad revs/minute\n", optarg); 238*51151Sbostic break; 239*51151Sbostic case 's': /* used for LFS */ 240*51151Sbostic if ((fssize = atoi(optarg)) <= 0) 241*51151Sbostic fatal("%s: bad file system size", optarg); 242*51151Sbostic break; 243*51151Sbostic case 't': 244*51151Sbostic if ((ntracks = atoi(optarg)) <= 0) 245*51151Sbostic fatal("%s: bad total tracks", optarg); 246*51151Sbostic break; 247*51151Sbostic case 'u': 248*51151Sbostic if ((nsectors = atoi(optarg)) <= 0) 249*51151Sbostic fatal("%s: bad sectors/track", optarg); 250*51151Sbostic break; 251*51151Sbostic case 'x': 252*51151Sbostic if ((cylspares = atoi(optarg)) < 0) 253*51151Sbostic fatal("%s: bad spare sectors per cylinder", 254*51151Sbostic optarg); 255*51151Sbostic break; 256*51151Sbostic case '?': 257*51151Sbostic default: 258*51151Sbostic usage(); 259*51151Sbostic } 260*51151Sbostic argc -= optind; 261*51151Sbostic argv += optind; 262*51151Sbostic 263*51151Sbostic if (argc != 2 && (mfs || argc != 1)) 264*51151Sbostic usage(); 265*51151Sbostic 266*51151Sbostic /* 267*51151Sbostic * If the -N flag isn't specified, open the output file. If no path 268*51151Sbostic * prefix, try /dev/r%s and then /dev/%s. 269*51151Sbostic */ 270*51151Sbostic special = argv[0]; 271*51151Sbostic if (index(special, '/') == NULL) { 272*51151Sbostic (void)sprintf(device, "%sr%s", _PATH_DEV, special); 273*51151Sbostic if (stat(device, &st) == -1) 274*51151Sbostic (void)sprintf(device, "%s%s", _PATH_DEV, special); 275*51151Sbostic special = device; 276*51151Sbostic } 277*51151Sbostic if (!Nflag) { 278*51151Sbostic fso = open(special, 279*51151Sbostic (debug ? O_CREAT : 0) | O_WRONLY, DEFFILEMODE); 280*51151Sbostic if (fso < 0) 281*51151Sbostic fatal("%s: %s", special, strerror(errno)); 282*51151Sbostic } else 283*51151Sbostic fso = -1; 284*51151Sbostic 285*51151Sbostic /* Open the input file. */ 286*51151Sbostic fsi = open(special, O_RDONLY); 287*51151Sbostic if (fsi < 0) 288*51151Sbostic fatal("%s: %s", special, strerror(errno)); 289*51151Sbostic if (fstat(fsi, &st) < 0) 290*51151Sbostic fatal("%s: %s", special, strerror(errno)); 291*51151Sbostic 292*51151Sbostic if (!debug && !mfs && S_ISCHR(st.st_mode)) 293*51151Sbostic (void)printf("%s: %s: not a character-special device\n", 294*51151Sbostic progname, special); 295*51151Sbostic cp = index(argv[0], '\0') - 1; 296*51151Sbostic if (!debug && (cp == 0 || (*cp < 'a' || *cp > 'h') && !isdigit(*cp))) 297*51151Sbostic fatal("%s: can't figure out file system partition", argv[0]); 298*51151Sbostic 299*51151Sbostic #ifdef COMPAT 300*51151Sbostic if (!mfs && disktype == NULL) 301*51151Sbostic disktype = argv[1]; 302*51151Sbostic #endif 303*51151Sbostic if (debug) 304*51151Sbostic lp = debug_readlabel(fsi); 305*51151Sbostic else 306*51151Sbostic lp = getdisklabel(special, fsi); 307*51151Sbostic 308*51151Sbostic if (isdigit(*cp)) 309*51151Sbostic pp = &lp->d_partitions[0]; 310*51151Sbostic else 311*51151Sbostic pp = &lp->d_partitions[*cp - 'a']; 312*51151Sbostic if (pp->p_size == 0) 313*51151Sbostic fatal("%s: `%c' partition is unavailable", argv[0], *cp); 314*51151Sbostic 315*51151Sbostic /* If we're making a LFS, we break out here */ 316*51151Sbostic if (lfs) 317*51151Sbostic exit(make_lfs(fso, lp, pp, minfree, bsize, segsize)); 318*51151Sbostic 319*51151Sbostic if (fssize == 0) 320*51151Sbostic fssize = pp->p_size; 321*51151Sbostic if (fssize > pp->p_size && !mfs) 322*51151Sbostic fatal("%s: maximum file system size on the `%c' partition is %d", 323*51151Sbostic argv[0], *cp, pp->p_size); 324*51151Sbostic if (rpm == 0) { 325*51151Sbostic rpm = lp->d_rpm; 326*51151Sbostic if (rpm <= 0) 327*51151Sbostic rpm = 3600; 328*51151Sbostic } 329*51151Sbostic if (ntracks == 0) { 330*51151Sbostic ntracks = lp->d_ntracks; 331*51151Sbostic if (ntracks <= 0) 332*51151Sbostic fatal("%s: no default #tracks", argv[0]); 333*51151Sbostic } 334*51151Sbostic if (nsectors == 0) { 335*51151Sbostic nsectors = lp->d_nsectors; 336*51151Sbostic if (nsectors <= 0) 337*51151Sbostic fatal("%s: no default #sectors/track", argv[0]); 338*51151Sbostic } 339*51151Sbostic if (sectorsize == 0) { 340*51151Sbostic sectorsize = lp->d_secsize; 341*51151Sbostic if (sectorsize <= 0) 342*51151Sbostic fatal("%s: no default sector size", argv[0]); 343*51151Sbostic } 344*51151Sbostic if (trackskew == -1) { 345*51151Sbostic trackskew = lp->d_trackskew; 346*51151Sbostic if (trackskew < 0) 347*51151Sbostic trackskew = 0; 348*51151Sbostic } 349*51151Sbostic if (interleave == 0) { 350*51151Sbostic interleave = lp->d_interleave; 351*51151Sbostic if (interleave <= 0) 352*51151Sbostic interleave = 1; 353*51151Sbostic } 354*51151Sbostic if (fsize == 0) { 355*51151Sbostic fsize = pp->p_fsize; 356*51151Sbostic if (fsize <= 0) 357*51151Sbostic fsize = MAX(DFL_FRAGSIZE, lp->d_secsize); 358*51151Sbostic } 359*51151Sbostic if (bsize == 0) { 360*51151Sbostic bsize = pp->p_frag * pp->p_fsize; 361*51151Sbostic if (bsize <= 0) 362*51151Sbostic bsize = MIN(DFL_BLKSIZE, 8 * fsize); 363*51151Sbostic } 364*51151Sbostic if (density == 0) 365*51151Sbostic density = NFPI * fsize; 366*51151Sbostic if (minfree < 10 && opt != FS_OPTSPACE) { 367*51151Sbostic fprintf(stderr, "Warning: changing optimization to space "); 368*51151Sbostic fprintf(stderr, "because minfree is less than 10%%\n"); 369*51151Sbostic opt = FS_OPTSPACE; 370*51151Sbostic } 371*51151Sbostic if (trackspares == -1) { 372*51151Sbostic trackspares = lp->d_sparespertrack; 373*51151Sbostic if (trackspares < 0) 374*51151Sbostic trackspares = 0; 375*51151Sbostic } 376*51151Sbostic nphyssectors = nsectors + trackspares; 377*51151Sbostic if (cylspares == -1) { 378*51151Sbostic cylspares = lp->d_sparespercyl; 379*51151Sbostic if (cylspares < 0) 380*51151Sbostic cylspares = 0; 381*51151Sbostic } 382*51151Sbostic secpercyl = nsectors * ntracks - cylspares; 383*51151Sbostic if (secpercyl != lp->d_secpercyl) 384*51151Sbostic fprintf(stderr, "%s (%d) %s (%lu)\n", 385*51151Sbostic "Warning: calculated sectors per cylinder", secpercyl, 386*51151Sbostic "disagrees with disk label", lp->d_secpercyl); 387*51151Sbostic if (maxbpg == 0) 388*51151Sbostic maxbpg = MAXBLKPG(bsize); 389*51151Sbostic headswitch = lp->d_headswitch; 390*51151Sbostic trackseek = lp->d_trkseek; 391*51151Sbostic #ifdef notdef /* label may be 0 if faked up by kernel */ 392*51151Sbostic bbsize = lp->d_bbsize; 393*51151Sbostic sbsize = lp->d_sbsize; 394*51151Sbostic #endif 395*51151Sbostic oldpartition = *pp; 396*51151Sbostic #ifdef tahoe 397*51151Sbostic realsectorsize = sectorsize; 398*51151Sbostic if (sectorsize != DEV_BSIZE) { /* XXX */ 399*51151Sbostic int secperblk = DEV_BSIZE / sectorsize; 400*51151Sbostic 401*51151Sbostic sectorsize = DEV_BSIZE; 402*51151Sbostic nsectors /= secperblk; 403*51151Sbostic nphyssectors /= secperblk; 404*51151Sbostic secpercyl /= secperblk; 405*51151Sbostic fssize /= secperblk; 406*51151Sbostic pp->p_size /= secperblk; 407*51151Sbostic } 408*51151Sbostic #endif 409*51151Sbostic mkfs(pp, special, fsi, fso); 410*51151Sbostic #ifdef tahoe 411*51151Sbostic if (realsectorsize != DEV_BSIZE) 412*51151Sbostic pp->p_size *= DEV_BSIZE / realsectorsize; 413*51151Sbostic #endif 414*51151Sbostic if (!Nflag && bcmp(pp, &oldpartition, sizeof(oldpartition))) 415*51151Sbostic rewritelabel(special, fso, lp); 416*51151Sbostic if (!Nflag) 417*51151Sbostic close(fso); 418*51151Sbostic close(fsi); 419*51151Sbostic #ifdef MFS 420*51151Sbostic if (mfs) { 421*51151Sbostic struct mfs_args args; 422*51151Sbostic char buf[50]; 423*51151Sbostic 424*51151Sbostic (void)sprintf(buf, "mfs:%d", getpid()); 425*51151Sbostic args.name = buf; 426*51151Sbostic args.base = membase; 427*51151Sbostic args.size = fssize * sectorsize; 428*51151Sbostic if (mount(MOUNT_MFS, argv[1], mntflags, &args) < 0) 429*51151Sbostic fatal("%s: %s", argv[1], strerror(errno)); 430*51151Sbostic } 431*51151Sbostic #endif 432*51151Sbostic exit(0); 433*51151Sbostic } 434*51151Sbostic 435*51151Sbostic #ifdef COMPAT 436*51151Sbostic char lmsg[] = "%s: can't read disk label; disk type must be specified"; 437*51151Sbostic #else 438*51151Sbostic char lmsg[] = "%s: can't read disk label"; 439*51151Sbostic #endif 440*51151Sbostic 441*51151Sbostic static struct disklabel * 442*51151Sbostic getdisklabel(s, fd) 443*51151Sbostic char *s; 444*51151Sbostic int fd; 445*51151Sbostic { 446*51151Sbostic static struct disklabel lab; 447*51151Sbostic 448*51151Sbostic if (ioctl(fd, DIOCGDINFO, (char *)&lab) < 0) { 449*51151Sbostic #ifdef COMPAT 450*51151Sbostic if (disktype) { 451*51151Sbostic struct disklabel *lp, *getdiskbyname(); 452*51151Sbostic 453*51151Sbostic unlabeled++; 454*51151Sbostic lp = getdiskbyname(disktype); 455*51151Sbostic if (lp == NULL) 456*51151Sbostic fatal("%s: unknown disk type", disktype); 457*51151Sbostic return (lp); 458*51151Sbostic } 459*51151Sbostic #endif 460*51151Sbostic (void)fprintf(stderr, 461*51151Sbostic "%s: ioctl (GDINFO): %s\n", progname, strerror(errno)); 462*51151Sbostic fatal(lmsg, s); 463*51151Sbostic } 464*51151Sbostic return (&lab); 465*51151Sbostic } 466*51151Sbostic 467*51151Sbostic 468*51151Sbostic static struct disklabel * 469*51151Sbostic debug_readlabel(fd) 470*51151Sbostic int fd; 471*51151Sbostic { 472*51151Sbostic static struct disklabel lab; 473*51151Sbostic int n; 474*51151Sbostic 475*51151Sbostic if ((n = read(fd, &lab, sizeof(struct disklabel))) < 0) 476*51151Sbostic fatal("unable to read disk label: %s", strerror(errno)); 477*51151Sbostic else if (n < sizeof(struct disklabel)) 478*51151Sbostic fatal("short read of disklabel: %d of %d bytes", n, 479*51151Sbostic sizeof(struct disklabel)); 480*51151Sbostic return(&lab); 481*51151Sbostic } 482*51151Sbostic 483*51151Sbostic static void 484*51151Sbostic rewritelabel(s, fd, lp) 485*51151Sbostic char *s; 486*51151Sbostic int fd; 487*51151Sbostic register struct disklabel *lp; 488*51151Sbostic { 489*51151Sbostic #ifdef COMPAT 490*51151Sbostic if (unlabeled) 491*51151Sbostic return; 492*51151Sbostic #endif 493*51151Sbostic lp->d_checksum = 0; 494*51151Sbostic lp->d_checksum = dkcksum(lp); 495*51151Sbostic if (ioctl(fd, DIOCWDINFO, (char *)lp) < 0) { 496*51151Sbostic (void)fprintf(stderr, 497*51151Sbostic "%s: ioctl (WDINFO): %s\n", progname, strerror(errno)); 498*51151Sbostic fatal("%s: can't rewrite disk label", s); 499*51151Sbostic } 500*51151Sbostic #if vax 501*51151Sbostic if (lp->d_type == DTYPE_SMD && lp->d_flags & D_BADSECT) { 502*51151Sbostic register i; 503*51151Sbostic int cfd; 504*51151Sbostic daddr_t alt; 505*51151Sbostic char specname[64]; 506*51151Sbostic char blk[1024]; 507*51151Sbostic char *cp; 508*51151Sbostic 509*51151Sbostic /* 510*51151Sbostic * Make name for 'c' partition. 511*51151Sbostic */ 512*51151Sbostic strcpy(specname, s); 513*51151Sbostic cp = specname + strlen(specname) - 1; 514*51151Sbostic if (!isdigit(*cp)) 515*51151Sbostic *cp = 'c'; 516*51151Sbostic cfd = open(specname, O_WRONLY); 517*51151Sbostic if (cfd < 0) 518*51151Sbostic fatal("%s: %s", specname, strerror(errno)); 519*51151Sbostic bzero(blk, sizeof(blk)); 520*51151Sbostic *(struct disklabel *)(blk + LABELOFFSET) = *lp; 521*51151Sbostic alt = lp->d_ncylinders * lp->d_secpercyl - lp->d_nsectors; 522*51151Sbostic for (i = 1; i < 11 && i < lp->d_nsectors; i += 2) { 523*51151Sbostic if (lseek(cfd, (off_t)(alt + i) * lp->d_secsize, 524*51151Sbostic L_SET) == -1) 525*51151Sbostic fatal("lseek to badsector area: %s", 526*51151Sbostic strerror(errno)); 527*51151Sbostic if (write(cfd, blk, lp->d_secsize) < lp->d_secsize) 528*51151Sbostic fprintf(stderr, 529*51151Sbostic "%s: alternate label %d write: %s\n", 530*51151Sbostic progname, i/2, strerror(errno)); 531*51151Sbostic } 532*51151Sbostic close(cfd); 533*51151Sbostic } 534*51151Sbostic #endif 535*51151Sbostic } 536*51151Sbostic 537*51151Sbostic void 538*51151Sbostic usage() 539*51151Sbostic { 540*51151Sbostic if (mfs) { 541*51151Sbostic fprintf(stderr, 542*51151Sbostic "usage: mfs [ -fsoptions ] special-device mount-point\n"); 543*51151Sbostic } else 544*51151Sbostic fprintf(stderr, 545*51151Sbostic "usage: newfs [ -fsoptions ] special-device%s\n", 546*51151Sbostic #ifdef COMPAT 547*51151Sbostic " [device-type]"); 548*51151Sbostic #else 549*51151Sbostic ""); 550*51151Sbostic #endif 551*51151Sbostic fprintf(stderr, "where fsoptions are:\n"); 552*51151Sbostic fprintf(stderr, "\t-B LFS segment size\n"); 553*51151Sbostic fprintf(stderr, "\t-D debug\n"); 554*51151Sbostic fprintf(stderr, "\t-F mount flags\n"); 555*51151Sbostic fprintf(stderr, "\t-L create LFS file system\n"); 556*51151Sbostic fprintf(stderr, 557*51151Sbostic "\t-N do not create file system, just print out parameters\n"); 558*51151Sbostic fprintf(stderr, "\t-S sector size\n"); 559*51151Sbostic #ifdef COMPAT 560*51151Sbostic fprintf(stderr, "\t-T disktype\n"); 561*51151Sbostic #endif 562*51151Sbostic fprintf(stderr, "\t-a maximum contiguous blocks\n"); 563*51151Sbostic fprintf(stderr, "\t-b block size\n"); 564*51151Sbostic fprintf(stderr, "\t-c cylinders/group\n"); 565*51151Sbostic fprintf(stderr, "\t-d rotational delay between contiguous blocks\n"); 566*51151Sbostic fprintf(stderr, "\t-e maximum blocks per file in a cylinder group\n"); 567*51151Sbostic fprintf(stderr, "\t-f frag size\n"); 568*51151Sbostic fprintf(stderr, "\t-i number of bytes per inode\n"); 569*51151Sbostic fprintf(stderr, "\t-k sector 0 skew, per track\n"); 570*51151Sbostic fprintf(stderr, "\t-l hardware sector interleave\n"); 571*51151Sbostic fprintf(stderr, "\t-m minimum free space %%\n"); 572*51151Sbostic fprintf(stderr, "\t-n number of distinguished rotational positions\n"); 573*51151Sbostic fprintf(stderr, "\t-o optimization preference (`space' or `time')\n"); 574*51151Sbostic fprintf(stderr, "\t-p spare sectors per track\n"); 575*51151Sbostic fprintf(stderr, "\t-r revolutions/minute\n"); 576*51151Sbostic fprintf(stderr, "\t-s file system size (sectors)\n"); 577*51151Sbostic fprintf(stderr, "\t-t tracks/cylinder\n"); 578*51151Sbostic fprintf(stderr, "\t-u sectors/track\n"); 579*51151Sbostic fprintf(stderr, "\t-x spare sectors per cylinder\n"); 580*51151Sbostic exit(1); 581*51151Sbostic } 582