xref: /titanic_52/usr/src/cmd/fs.d/ufs/tunefs/tunefs.c (revision d1a180b0452ce86577a43be3245d2eacdeec1a34)
17c478bd9Sstevel@tonic-gate /*
27c478bd9Sstevel@tonic-gate  * CDDL HEADER START
37c478bd9Sstevel@tonic-gate  *
47c478bd9Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
5*d1a180b0Smaheshvs  * Common Development and Distribution License (the "License").
6*d1a180b0Smaheshvs  * You may not use this file except in compliance with the License.
77c478bd9Sstevel@tonic-gate  *
87c478bd9Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
97c478bd9Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
107c478bd9Sstevel@tonic-gate  * See the License for the specific language governing permissions
117c478bd9Sstevel@tonic-gate  * and limitations under the License.
127c478bd9Sstevel@tonic-gate  *
137c478bd9Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
147c478bd9Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
157c478bd9Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
167c478bd9Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
177c478bd9Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
187c478bd9Sstevel@tonic-gate  *
197c478bd9Sstevel@tonic-gate  * CDDL HEADER END
207c478bd9Sstevel@tonic-gate  */
217c478bd9Sstevel@tonic-gate /*
226451fdbcSvsakar  * Copyright 2005 Sun Microsystems, Inc.  All rights reserved.
237c478bd9Sstevel@tonic-gate  * Use is subject to license terms.
247c478bd9Sstevel@tonic-gate  */
257c478bd9Sstevel@tonic-gate 
267c478bd9Sstevel@tonic-gate /*	Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T	*/
277c478bd9Sstevel@tonic-gate /*	  All Rights Reserved  	*/
287c478bd9Sstevel@tonic-gate 
297c478bd9Sstevel@tonic-gate /*
307c478bd9Sstevel@tonic-gate  * University Copyright- Copyright (c) 1982, 1986, 1988
317c478bd9Sstevel@tonic-gate  * The Regents of the University of California
327c478bd9Sstevel@tonic-gate  * All Rights Reserved
337c478bd9Sstevel@tonic-gate  *
347c478bd9Sstevel@tonic-gate  * University Acknowledgment- Portions of this document are derived from
357c478bd9Sstevel@tonic-gate  * software developed by the University of California, Berkeley, and its
367c478bd9Sstevel@tonic-gate  * contributors.
377c478bd9Sstevel@tonic-gate  */
387c478bd9Sstevel@tonic-gate 
397c478bd9Sstevel@tonic-gate #pragma ident	"%Z%%M%	%I%	%E% SMI"
407c478bd9Sstevel@tonic-gate 
417c478bd9Sstevel@tonic-gate /*
427c478bd9Sstevel@tonic-gate  * tunefs: change layout parameters to an existing file system.
437c478bd9Sstevel@tonic-gate  */
447c478bd9Sstevel@tonic-gate 
457c478bd9Sstevel@tonic-gate #include <string.h>
467c478bd9Sstevel@tonic-gate #include <unistd.h>
477c478bd9Sstevel@tonic-gate #include <stdlib.h>
487c478bd9Sstevel@tonic-gate #include <ustat.h>
497c478bd9Sstevel@tonic-gate #include <sys/param.h>
507c478bd9Sstevel@tonic-gate #include <sys/types.h>
517c478bd9Sstevel@tonic-gate #include <time.h>
527c478bd9Sstevel@tonic-gate #include <sys/mntent.h>
537c478bd9Sstevel@tonic-gate 
547c478bd9Sstevel@tonic-gate #define	bcopy(f, t, n)    memcpy(t, f, n)
557c478bd9Sstevel@tonic-gate #define	bzero(s, n)	memset(s, 0, n)
567c478bd9Sstevel@tonic-gate #define	bcmp(s, d, n)	memcmp(s, d, n)
577c478bd9Sstevel@tonic-gate 
587c478bd9Sstevel@tonic-gate #define	index(s, r)	strchr(s, r)
597c478bd9Sstevel@tonic-gate #define	rindex(s, r)	strrchr(s, r)
607c478bd9Sstevel@tonic-gate 
617c478bd9Sstevel@tonic-gate #include <sys/sysmacros.h>
627c478bd9Sstevel@tonic-gate #include <sys/stat.h>
637c478bd9Sstevel@tonic-gate #include <sys/fs/ufs_fs.h>
647c478bd9Sstevel@tonic-gate #include <sys/vnode.h>
657c478bd9Sstevel@tonic-gate #include <sys/fs/ufs_inode.h>
667c478bd9Sstevel@tonic-gate #include <fcntl.h>
677c478bd9Sstevel@tonic-gate #include <stdio.h>
687c478bd9Sstevel@tonic-gate #include <sys/mnttab.h>
697c478bd9Sstevel@tonic-gate #include <sys/vfstab.h>
707c478bd9Sstevel@tonic-gate #include <sys/ustat.h>
717c478bd9Sstevel@tonic-gate #include <sys/filio.h>
727c478bd9Sstevel@tonic-gate #include <sys/fs/ufs_filio.h>
737c478bd9Sstevel@tonic-gate 
747c478bd9Sstevel@tonic-gate extern offset_t llseek();
757c478bd9Sstevel@tonic-gate 
767c478bd9Sstevel@tonic-gate union {
777c478bd9Sstevel@tonic-gate 	struct	fs sb;
787c478bd9Sstevel@tonic-gate 	char pad[SBSIZE];
797c478bd9Sstevel@tonic-gate } sbun;
807c478bd9Sstevel@tonic-gate #define	sblock sbun.sb
817c478bd9Sstevel@tonic-gate 
827c478bd9Sstevel@tonic-gate int fi;
837c478bd9Sstevel@tonic-gate struct ustat ustatarea;
847c478bd9Sstevel@tonic-gate extern int	optind;
857c478bd9Sstevel@tonic-gate extern char	*optarg;
867c478bd9Sstevel@tonic-gate 
877c478bd9Sstevel@tonic-gate static void usage();
88*d1a180b0Smaheshvs static void getsb(struct fs *, char *);
89*d1a180b0Smaheshvs static void bwrite(diskaddr_t, char *, int);
907c478bd9Sstevel@tonic-gate static void fatal();
91*d1a180b0Smaheshvs static int bread(diskaddr_t, char *, int);
92*d1a180b0Smaheshvs static int isnumber(char *);
937c478bd9Sstevel@tonic-gate 
947c478bd9Sstevel@tonic-gate extern char *getfullrawname(), *getfullblkname();
957c478bd9Sstevel@tonic-gate 
967c478bd9Sstevel@tonic-gate static void
977c478bd9Sstevel@tonic-gate searchvfstab(char **specialp)
987c478bd9Sstevel@tonic-gate {
997c478bd9Sstevel@tonic-gate 	FILE *vfstab;
1007c478bd9Sstevel@tonic-gate 	struct vfstab vfsbuf;
1017c478bd9Sstevel@tonic-gate 	char *blockspecial;
1027c478bd9Sstevel@tonic-gate 
1037c478bd9Sstevel@tonic-gate 	blockspecial = getfullblkname(*specialp);
1047c478bd9Sstevel@tonic-gate 	if (blockspecial == NULL)
1057c478bd9Sstevel@tonic-gate 		blockspecial = *specialp;
1067c478bd9Sstevel@tonic-gate 
1077c478bd9Sstevel@tonic-gate 	if ((vfstab = fopen(VFSTAB, "r")) == NULL) {
1087c478bd9Sstevel@tonic-gate 		fprintf(stderr, "%s: ", VFSTAB);
1097c478bd9Sstevel@tonic-gate 		perror("open");
1107c478bd9Sstevel@tonic-gate 	}
1117c478bd9Sstevel@tonic-gate 	while (getvfsent(vfstab, &vfsbuf) == NULL)
1127c478bd9Sstevel@tonic-gate 		if (strcmp(vfsbuf.vfs_fstype, MNTTYPE_UFS) == 0)
1137c478bd9Sstevel@tonic-gate 			if ((strcmp(vfsbuf.vfs_mountp, *specialp) == 0) ||
1147c478bd9Sstevel@tonic-gate 			    (strcmp(vfsbuf.vfs_special, *specialp) == 0) ||
1157c478bd9Sstevel@tonic-gate 			    (strcmp(vfsbuf.vfs_special, blockspecial) == 0) ||
1167c478bd9Sstevel@tonic-gate 			    (strcmp(vfsbuf.vfs_fsckdev, *specialp) == 0)) {
1177c478bd9Sstevel@tonic-gate 				*specialp = strdup(vfsbuf.vfs_special);
1187c478bd9Sstevel@tonic-gate 				return;
1197c478bd9Sstevel@tonic-gate 			}
1207c478bd9Sstevel@tonic-gate 	fclose(vfstab);
1217c478bd9Sstevel@tonic-gate }
1227c478bd9Sstevel@tonic-gate 
1237c478bd9Sstevel@tonic-gate static void
1247c478bd9Sstevel@tonic-gate searchmnttab(char **specialp, char **mountpointp)
1257c478bd9Sstevel@tonic-gate {
1267c478bd9Sstevel@tonic-gate 	FILE *mnttab;
1277c478bd9Sstevel@tonic-gate 	struct mnttab mntbuf;
1287c478bd9Sstevel@tonic-gate 	char *blockspecial;
1297c478bd9Sstevel@tonic-gate 
1307c478bd9Sstevel@tonic-gate 	blockspecial = getfullblkname(*specialp);
1317c478bd9Sstevel@tonic-gate 	if (blockspecial == NULL)
1327c478bd9Sstevel@tonic-gate 		blockspecial = *specialp;
1337c478bd9Sstevel@tonic-gate 
1347c478bd9Sstevel@tonic-gate 	if ((mnttab = fopen(MNTTAB, "r")) == NULL)
1357c478bd9Sstevel@tonic-gate 		return;
1367c478bd9Sstevel@tonic-gate 	while (getmntent(mnttab, &mntbuf) == NULL)
1377c478bd9Sstevel@tonic-gate 		if (strcmp(mntbuf.mnt_fstype, MNTTYPE_UFS) == 0)
1387c478bd9Sstevel@tonic-gate 			if ((strcmp(mntbuf.mnt_mountp, *specialp) == 0) ||
1397c478bd9Sstevel@tonic-gate 			    (strcmp(mntbuf.mnt_special, blockspecial) == 0) ||
1407c478bd9Sstevel@tonic-gate 			    (strcmp(mntbuf.mnt_special, *specialp) == 0)) {
1417c478bd9Sstevel@tonic-gate 				*specialp = strdup(mntbuf.mnt_special);
1427c478bd9Sstevel@tonic-gate 				*mountpointp = strdup(mntbuf.mnt_mountp);
1437c478bd9Sstevel@tonic-gate 				return;
1447c478bd9Sstevel@tonic-gate 			}
1457c478bd9Sstevel@tonic-gate 	fclose(mnttab);
1467c478bd9Sstevel@tonic-gate }
1477c478bd9Sstevel@tonic-gate 
148*d1a180b0Smaheshvs int
149*d1a180b0Smaheshvs main(int argc, char *argv[])
1507c478bd9Sstevel@tonic-gate {
1517c478bd9Sstevel@tonic-gate 	char *special, *name, *mountpoint = NULL;
1527c478bd9Sstevel@tonic-gate 	struct stat64 st;
1537c478bd9Sstevel@tonic-gate 	int i, mountfd;
1547c478bd9Sstevel@tonic-gate 	int Aflag = 0;
1557c478bd9Sstevel@tonic-gate 	char *chg[2];
1567c478bd9Sstevel@tonic-gate 	int	opt;
1577c478bd9Sstevel@tonic-gate 	struct fiotune fiotune;
1587c478bd9Sstevel@tonic-gate 
1597c478bd9Sstevel@tonic-gate 
1607c478bd9Sstevel@tonic-gate 	if (argc < 3)
1617c478bd9Sstevel@tonic-gate 		usage();
1627c478bd9Sstevel@tonic-gate 	special = argv[argc - 1];
1637c478bd9Sstevel@tonic-gate 
1647c478bd9Sstevel@tonic-gate 	/*
1657c478bd9Sstevel@tonic-gate 	 * For performance, don't search mnttab unless necessary
1667c478bd9Sstevel@tonic-gate 	 */
1677c478bd9Sstevel@tonic-gate 
1687c478bd9Sstevel@tonic-gate 	if (stat64(special, &st) >= 0) {
1697c478bd9Sstevel@tonic-gate 		/*
1707c478bd9Sstevel@tonic-gate 		 * If mounted directory, search mnttab for special
1717c478bd9Sstevel@tonic-gate 		 */
1727c478bd9Sstevel@tonic-gate 		if ((st.st_mode & S_IFMT) == S_IFDIR) {
1737c478bd9Sstevel@tonic-gate 			if (st.st_ino == UFSROOTINO)
1747c478bd9Sstevel@tonic-gate 				searchmnttab(&special, &mountpoint);
1757c478bd9Sstevel@tonic-gate 		/*
1767c478bd9Sstevel@tonic-gate 		 * If mounted device, search mnttab for mountpoint
1777c478bd9Sstevel@tonic-gate 		 */
1787c478bd9Sstevel@tonic-gate 		} else if ((st.st_mode & S_IFMT) == S_IFBLK ||
1797c478bd9Sstevel@tonic-gate 			    (st.st_mode & S_IFMT) == S_IFCHR) {
1807c478bd9Sstevel@tonic-gate 				if (ustat(st.st_rdev, &ustatarea) >= 0)
1817c478bd9Sstevel@tonic-gate 					searchmnttab(&special, &mountpoint);
1827c478bd9Sstevel@tonic-gate 		}
1837c478bd9Sstevel@tonic-gate 	}
1847c478bd9Sstevel@tonic-gate 	/*
1857c478bd9Sstevel@tonic-gate 	 * Doesn't appear to be mounted; take ``unmounted'' path
1867c478bd9Sstevel@tonic-gate 	 */
1877c478bd9Sstevel@tonic-gate 	if (mountpoint == NULL)
1887c478bd9Sstevel@tonic-gate 		searchvfstab(&special);
1897c478bd9Sstevel@tonic-gate 
1907c478bd9Sstevel@tonic-gate 	if ((special = getfullrawname(special)) == NULL) {
1917c478bd9Sstevel@tonic-gate 		fprintf(stderr, "tunefs: malloc failed\n");
1927c478bd9Sstevel@tonic-gate 		exit(32);
1937c478bd9Sstevel@tonic-gate 	}
1947c478bd9Sstevel@tonic-gate 
1957c478bd9Sstevel@tonic-gate 	if (*special == '\0') {
1967c478bd9Sstevel@tonic-gate 		fprintf(stderr, "tunefs: Could not find raw device for %s\n",
1977c478bd9Sstevel@tonic-gate 		    argv[argc -1]);
1987c478bd9Sstevel@tonic-gate 		exit(32);
1997c478bd9Sstevel@tonic-gate 	}
2007c478bd9Sstevel@tonic-gate 
2017c478bd9Sstevel@tonic-gate 	if (stat64(special, &st) < 0) {
2027c478bd9Sstevel@tonic-gate 		fprintf(stderr, "tunefs: "); perror(special);
2037c478bd9Sstevel@tonic-gate 		exit(31+1);
2047c478bd9Sstevel@tonic-gate 	}
2057c478bd9Sstevel@tonic-gate 
2067c478bd9Sstevel@tonic-gate 	/*
2077c478bd9Sstevel@tonic-gate 	 * If a mountpoint has been found then we will ioctl() the file
2087c478bd9Sstevel@tonic-gate 	 * system instead of writing to the file system's device
2097c478bd9Sstevel@tonic-gate 	 */
2107c478bd9Sstevel@tonic-gate 	/* ustat() ok because max number of UFS inodes can fit in ino_t */
2117c478bd9Sstevel@tonic-gate 	if (ustat(st.st_rdev, &ustatarea) >= 0) {
2127c478bd9Sstevel@tonic-gate 		if (mountpoint == NULL) {
2137c478bd9Sstevel@tonic-gate 			printf("%s is mounted, can't tunefs\n", special);
2147c478bd9Sstevel@tonic-gate 			exit(32);
2157c478bd9Sstevel@tonic-gate 		}
2167c478bd9Sstevel@tonic-gate 	} else
2177c478bd9Sstevel@tonic-gate 		mountpoint = NULL;
2187c478bd9Sstevel@tonic-gate 
2197c478bd9Sstevel@tonic-gate 	if ((st.st_mode & S_IFMT) != S_IFBLK &&
2207c478bd9Sstevel@tonic-gate 	    (st.st_mode & S_IFMT) != S_IFCHR)
2217c478bd9Sstevel@tonic-gate 		fatal("%s: not a block or character device", special);
2227c478bd9Sstevel@tonic-gate 	getsb(&sblock, special);
2237c478bd9Sstevel@tonic-gate 	while ((opt = getopt(argc, argv, "o:m:e:d:a:AV")) != EOF) {
2247c478bd9Sstevel@tonic-gate 		switch (opt) {
2257c478bd9Sstevel@tonic-gate 
2267c478bd9Sstevel@tonic-gate 		case 'A':
2277c478bd9Sstevel@tonic-gate 			Aflag++;
2287c478bd9Sstevel@tonic-gate 			continue;
2297c478bd9Sstevel@tonic-gate 
2307c478bd9Sstevel@tonic-gate 		case 'a':
2317c478bd9Sstevel@tonic-gate 			name = "maximum contiguous block count";
2327c478bd9Sstevel@tonic-gate 			if (!isnumber(optarg))
2337c478bd9Sstevel@tonic-gate 				fatal("%s: %s must be >= 1", *argv, name);
2347c478bd9Sstevel@tonic-gate 			i = atoi(optarg);
2357c478bd9Sstevel@tonic-gate 			if (i < 1)
2367c478bd9Sstevel@tonic-gate 				fatal("%s: %s must be >= 1", *argv, name);
2377c478bd9Sstevel@tonic-gate 			fprintf(stdout, "%s changes from %d to %d\n",
2387c478bd9Sstevel@tonic-gate 				name, sblock.fs_maxcontig, i);
2397c478bd9Sstevel@tonic-gate 			sblock.fs_maxcontig = i;
2407c478bd9Sstevel@tonic-gate 			continue;
2417c478bd9Sstevel@tonic-gate 
2427c478bd9Sstevel@tonic-gate 		case 'd':
2437c478bd9Sstevel@tonic-gate 			sblock.fs_rotdelay = 0;
2447c478bd9Sstevel@tonic-gate 			continue;
2457c478bd9Sstevel@tonic-gate 
2467c478bd9Sstevel@tonic-gate 		case 'e':
2477c478bd9Sstevel@tonic-gate 			name =
2487c478bd9Sstevel@tonic-gate 			    "maximum blocks per file in a cylinder group";
2497c478bd9Sstevel@tonic-gate 			if (!isnumber(optarg))
2507c478bd9Sstevel@tonic-gate 				fatal("%s: %s must be >= 1", *argv, name);
2517c478bd9Sstevel@tonic-gate 			i = atoi(optarg);
2527c478bd9Sstevel@tonic-gate 			if (i < 1)
2537c478bd9Sstevel@tonic-gate 				fatal("%s: %s must be >= 1", *argv, name);
2547c478bd9Sstevel@tonic-gate 			fprintf(stdout, "%s changes from %d to %d\n",
2557c478bd9Sstevel@tonic-gate 				name, sblock.fs_maxbpg, i);
2567c478bd9Sstevel@tonic-gate 			sblock.fs_maxbpg = i;
2577c478bd9Sstevel@tonic-gate 			continue;
2587c478bd9Sstevel@tonic-gate 
2597c478bd9Sstevel@tonic-gate 		case 'm':
2607c478bd9Sstevel@tonic-gate 			name = "minimum percentage of free space";
2617c478bd9Sstevel@tonic-gate 			if (!isnumber(optarg))
2627c478bd9Sstevel@tonic-gate 				fatal("%s: bad %s", *argv, name);
2637c478bd9Sstevel@tonic-gate 			i = atoi(optarg);
2647c478bd9Sstevel@tonic-gate 			if (i < 0 || i > 99)
2657c478bd9Sstevel@tonic-gate 				fatal("%s: bad %s", *argv, name);
2667c478bd9Sstevel@tonic-gate 			fprintf(stdout,
2677c478bd9Sstevel@tonic-gate 				"%s changes from %d%% to %d%%\n",
2687c478bd9Sstevel@tonic-gate 				name, sblock.fs_minfree, i);
2697c478bd9Sstevel@tonic-gate 			sblock.fs_minfree = i;
2707c478bd9Sstevel@tonic-gate 			continue;
2717c478bd9Sstevel@tonic-gate 
2727c478bd9Sstevel@tonic-gate 		case 'o':
2737c478bd9Sstevel@tonic-gate 			name = "optimization preference";
2747c478bd9Sstevel@tonic-gate 			chg[FS_OPTSPACE] = "space";
2757c478bd9Sstevel@tonic-gate 			chg[FS_OPTTIME] = "time";
2767c478bd9Sstevel@tonic-gate 			if (strcmp(optarg, chg[FS_OPTSPACE]) == 0)
2777c478bd9Sstevel@tonic-gate 				i = FS_OPTSPACE;
2787c478bd9Sstevel@tonic-gate 			else if (strcmp(optarg, chg[FS_OPTTIME]) == 0)
2797c478bd9Sstevel@tonic-gate 				i = FS_OPTTIME;
2807c478bd9Sstevel@tonic-gate 			else
2817c478bd9Sstevel@tonic-gate 			fatal("%s: bad %s (options are `space' or `time')",
2827c478bd9Sstevel@tonic-gate 					optarg, name);
2837c478bd9Sstevel@tonic-gate 			if (sblock.fs_optim == i) {
2847c478bd9Sstevel@tonic-gate 				fprintf(stdout,
2857c478bd9Sstevel@tonic-gate 					"%s remains unchanged as %s\n",
2867c478bd9Sstevel@tonic-gate 					name, chg[i]);
2877c478bd9Sstevel@tonic-gate 				continue;
2887c478bd9Sstevel@tonic-gate 			}
2897c478bd9Sstevel@tonic-gate 			fprintf(stdout,
2907c478bd9Sstevel@tonic-gate 				"%s changes from %s to %s\n",
2917c478bd9Sstevel@tonic-gate 				name, chg[sblock.fs_optim], chg[i]);
2927c478bd9Sstevel@tonic-gate 			sblock.fs_optim = i;
2937c478bd9Sstevel@tonic-gate 			continue;
2947c478bd9Sstevel@tonic-gate 
2957c478bd9Sstevel@tonic-gate 		case 'V':
2967c478bd9Sstevel@tonic-gate 			{
2977c478bd9Sstevel@tonic-gate 				char	*opt_text;
2987c478bd9Sstevel@tonic-gate 				int	opt_count;
2997c478bd9Sstevel@tonic-gate 
3007c478bd9Sstevel@tonic-gate 				(void) fprintf(stdout, "tunefs -F ufs ");
3017c478bd9Sstevel@tonic-gate 				for (opt_count = 1; opt_count < argc;
3027c478bd9Sstevel@tonic-gate 				    opt_count++) {
3037c478bd9Sstevel@tonic-gate 					opt_text = argv[opt_count];
3047c478bd9Sstevel@tonic-gate 					if (opt_text)
3057c478bd9Sstevel@tonic-gate 						(void) fprintf(stdout, " %s ",
3067c478bd9Sstevel@tonic-gate 						    opt_text);
3077c478bd9Sstevel@tonic-gate 				}
3087c478bd9Sstevel@tonic-gate 				(void) fprintf(stdout, "\n");
3097c478bd9Sstevel@tonic-gate 			}
3107c478bd9Sstevel@tonic-gate 			break;
3117c478bd9Sstevel@tonic-gate 
3127c478bd9Sstevel@tonic-gate 		default:
3137c478bd9Sstevel@tonic-gate 			usage();
3147c478bd9Sstevel@tonic-gate 		}
3157c478bd9Sstevel@tonic-gate 	}
3167c478bd9Sstevel@tonic-gate 	if ((argc - optind) != 1)
3177c478bd9Sstevel@tonic-gate 		usage();
3187c478bd9Sstevel@tonic-gate 	if (mountpoint) {
3197c478bd9Sstevel@tonic-gate 		mountfd = open(mountpoint, O_RDONLY);
3207c478bd9Sstevel@tonic-gate 		if (mountfd == -1) {
3217c478bd9Sstevel@tonic-gate 			perror(mountpoint);
3227c478bd9Sstevel@tonic-gate 			fprintf(stderr,
3237c478bd9Sstevel@tonic-gate 				"tunefs: can't tune %s\n", mountpoint);
3247c478bd9Sstevel@tonic-gate 			exit(32);
3257c478bd9Sstevel@tonic-gate 		}
3267c478bd9Sstevel@tonic-gate 		fiotune.maxcontig = sblock.fs_maxcontig;
3277c478bd9Sstevel@tonic-gate 		fiotune.rotdelay = sblock.fs_rotdelay;
3287c478bd9Sstevel@tonic-gate 		fiotune.maxbpg = sblock.fs_maxbpg;
3297c478bd9Sstevel@tonic-gate 		fiotune.minfree = sblock.fs_minfree;
3307c478bd9Sstevel@tonic-gate 		fiotune.optim = sblock.fs_optim;
3317c478bd9Sstevel@tonic-gate 		if (ioctl(mountfd, _FIOTUNE, &fiotune) == -1) {
3327c478bd9Sstevel@tonic-gate 			perror(mountpoint);
3337c478bd9Sstevel@tonic-gate 			fprintf(stderr,
3347c478bd9Sstevel@tonic-gate 				"tunefs: can't tune %s\n", mountpoint);
3357c478bd9Sstevel@tonic-gate 			exit(32);
3367c478bd9Sstevel@tonic-gate 		}
3377c478bd9Sstevel@tonic-gate 		close(mountfd);
3387c478bd9Sstevel@tonic-gate 	} else {
3397c478bd9Sstevel@tonic-gate 		bwrite((diskaddr_t)SBLOCK, (char *)&sblock, SBSIZE);
3407c478bd9Sstevel@tonic-gate 
3417c478bd9Sstevel@tonic-gate 		if (Aflag)
3427c478bd9Sstevel@tonic-gate 			for (i = 0; i < sblock.fs_ncg; i++)
3437c478bd9Sstevel@tonic-gate 				bwrite(fsbtodb(&sblock, cgsblock(&sblock, i)),
3447c478bd9Sstevel@tonic-gate 				    (char *)&sblock, SBSIZE);
3457c478bd9Sstevel@tonic-gate 	}
3467c478bd9Sstevel@tonic-gate 
3477c478bd9Sstevel@tonic-gate 	close(fi);
348*d1a180b0Smaheshvs 	return (0);
3497c478bd9Sstevel@tonic-gate }
3507c478bd9Sstevel@tonic-gate 
3517c478bd9Sstevel@tonic-gate void
3527c478bd9Sstevel@tonic-gate usage()
3537c478bd9Sstevel@tonic-gate {
3547c478bd9Sstevel@tonic-gate 	fprintf(stderr, "ufs usage: tunefs tuneup-options special-device\n");
3557c478bd9Sstevel@tonic-gate 	fprintf(stderr, "where tuneup-options are:\n");
3567c478bd9Sstevel@tonic-gate 	fprintf(stderr, "\t-a maximum contiguous blocks\n");
3577c478bd9Sstevel@tonic-gate 	fprintf(stderr, "\t-d rotational delay between contiguous blocks\n");
3587c478bd9Sstevel@tonic-gate 	fprintf(stderr, "\t-e maximum blocks per file in a cylinder group\n");
3597c478bd9Sstevel@tonic-gate 	fprintf(stderr, "\t-m minimum percentage of free space\n");
3607c478bd9Sstevel@tonic-gate 	fprintf(stderr, "\t-o optimization preference (`space' or `time')\n");
3617c478bd9Sstevel@tonic-gate 	exit(31+2);
3627c478bd9Sstevel@tonic-gate }
3637c478bd9Sstevel@tonic-gate 
3647c478bd9Sstevel@tonic-gate void
365*d1a180b0Smaheshvs getsb(struct fs *fs, char *file)
3667c478bd9Sstevel@tonic-gate {
3677c478bd9Sstevel@tonic-gate 
3687c478bd9Sstevel@tonic-gate 	fi = open64(file, O_RDWR);
3697c478bd9Sstevel@tonic-gate 	if (fi < 0) {
3707c478bd9Sstevel@tonic-gate 		fprintf(stderr, "Cannot open ");
3717c478bd9Sstevel@tonic-gate 		perror(file);
3727c478bd9Sstevel@tonic-gate 		exit(31+3);
3737c478bd9Sstevel@tonic-gate 	}
3747c478bd9Sstevel@tonic-gate 	if (bread((diskaddr_t)SBLOCK, (char *)fs, SBSIZE)) {
3757c478bd9Sstevel@tonic-gate 		fprintf(stderr, "Bad super block ");
3767c478bd9Sstevel@tonic-gate 		perror(file);
3777c478bd9Sstevel@tonic-gate 		exit(31+4);
3787c478bd9Sstevel@tonic-gate 	}
3797c478bd9Sstevel@tonic-gate 	if ((fs->fs_magic != FS_MAGIC) && (fs->fs_magic != MTB_UFS_MAGIC)) {
3807c478bd9Sstevel@tonic-gate 		fprintf(stderr, "%s: bad magic number\n", file);
3817c478bd9Sstevel@tonic-gate 		exit(31+5);
3827c478bd9Sstevel@tonic-gate 	}
3836451fdbcSvsakar 	if (fs->fs_magic == FS_MAGIC &&
3846451fdbcSvsakar 	    (fs->fs_version != UFS_EFISTYLE4NONEFI_VERSION_2 &&
3856451fdbcSvsakar 	    fs->fs_version != UFS_VERSION_MIN)) {
3866451fdbcSvsakar 		fprintf(stderr, "%s: unrecognized ufs version: %d\n", file,
3876451fdbcSvsakar 		    fs->fs_version);
3886451fdbcSvsakar 		exit(31+5);
3896451fdbcSvsakar 	}
3907c478bd9Sstevel@tonic-gate 	if (fs->fs_magic == MTB_UFS_MAGIC &&
3917c478bd9Sstevel@tonic-gate 	    (fs->fs_version > MTB_UFS_VERSION_1 ||
3927c478bd9Sstevel@tonic-gate 	    fs->fs_version < MTB_UFS_VERSION_MIN)) {
3937c478bd9Sstevel@tonic-gate 		fprintf(stderr, "%s: unrecognized ufs version: %d\n", file,
3947c478bd9Sstevel@tonic-gate 		    fs->fs_version);
3957c478bd9Sstevel@tonic-gate 		exit(31+5);
3967c478bd9Sstevel@tonic-gate 	}
3977c478bd9Sstevel@tonic-gate }
3987c478bd9Sstevel@tonic-gate 
3997c478bd9Sstevel@tonic-gate void
400*d1a180b0Smaheshvs bwrite(diskaddr_t blk, char *buf, int size)
4017c478bd9Sstevel@tonic-gate {
4027c478bd9Sstevel@tonic-gate 	if (llseek(fi, (offset_t)blk * DEV_BSIZE, 0) < 0) {
4037c478bd9Sstevel@tonic-gate 		perror("FS SEEK");
4047c478bd9Sstevel@tonic-gate 		exit(31+6);
4057c478bd9Sstevel@tonic-gate 	}
4067c478bd9Sstevel@tonic-gate 	if (write(fi, buf, size) != size) {
4077c478bd9Sstevel@tonic-gate 		perror("FS WRITE");
4087c478bd9Sstevel@tonic-gate 		exit(31+7);
4097c478bd9Sstevel@tonic-gate 	}
4107c478bd9Sstevel@tonic-gate }
4117c478bd9Sstevel@tonic-gate 
4127c478bd9Sstevel@tonic-gate int
413*d1a180b0Smaheshvs bread(diskaddr_t bno, char *buf, int cnt)
4147c478bd9Sstevel@tonic-gate {
4157c478bd9Sstevel@tonic-gate 	int	i;
4167c478bd9Sstevel@tonic-gate 
4177c478bd9Sstevel@tonic-gate 	if (llseek(fi, (offset_t)bno * DEV_BSIZE, 0) < 0) {
4187c478bd9Sstevel@tonic-gate 		fprintf(stderr, "bread: ");
4197c478bd9Sstevel@tonic-gate 		perror("llseek");
4207c478bd9Sstevel@tonic-gate 		return (1);
4217c478bd9Sstevel@tonic-gate 	}
4227c478bd9Sstevel@tonic-gate 	if ((i = read(fi, buf, cnt)) != cnt) {
4237c478bd9Sstevel@tonic-gate 		perror("read");
4247c478bd9Sstevel@tonic-gate 		for (i = 0; i < sblock.fs_bsize; i++)
4257c478bd9Sstevel@tonic-gate 			buf[i] = 0;
4267c478bd9Sstevel@tonic-gate 		return (1);
4277c478bd9Sstevel@tonic-gate 	}
4287c478bd9Sstevel@tonic-gate 	return (0);
4297c478bd9Sstevel@tonic-gate }
4307c478bd9Sstevel@tonic-gate 
4317c478bd9Sstevel@tonic-gate /* VARARGS1 */
4327c478bd9Sstevel@tonic-gate void
433*d1a180b0Smaheshvs fatal(char *fmt, char *arg1, char *arg2)
4347c478bd9Sstevel@tonic-gate {
4357c478bd9Sstevel@tonic-gate 	fprintf(stderr, "tunefs: ");
4367c478bd9Sstevel@tonic-gate 	fprintf(stderr, fmt, arg1, arg2);
4377c478bd9Sstevel@tonic-gate 	putc('\n', stderr);
4387c478bd9Sstevel@tonic-gate 	exit(31+10);
4397c478bd9Sstevel@tonic-gate }
4407c478bd9Sstevel@tonic-gate 
4417c478bd9Sstevel@tonic-gate 
4427c478bd9Sstevel@tonic-gate int
443*d1a180b0Smaheshvs isnumber(char *s)
4447c478bd9Sstevel@tonic-gate {
445*d1a180b0Smaheshvs 	int c;
4467c478bd9Sstevel@tonic-gate 
4477c478bd9Sstevel@tonic-gate 	while (c = *s++)
4487c478bd9Sstevel@tonic-gate 		if (c < '0' || c > '9')
4497c478bd9Sstevel@tonic-gate 			return (0);
4507c478bd9Sstevel@tonic-gate 	return (1);
4517c478bd9Sstevel@tonic-gate }
452