xref: /titanic_50/usr/src/lib/libadm/common/getvol.c (revision 7c478bd95313f5f23a4c958a745db2134aa03244)
1*7c478bd9Sstevel@tonic-gate /*
2*7c478bd9Sstevel@tonic-gate  * CDDL HEADER START
3*7c478bd9Sstevel@tonic-gate  *
4*7c478bd9Sstevel@tonic-gate  * The contents of this file are subject to the terms of the
5*7c478bd9Sstevel@tonic-gate  * Common Development and Distribution License, Version 1.0 only
6*7c478bd9Sstevel@tonic-gate  * (the "License").  You may not use this file except in compliance
7*7c478bd9Sstevel@tonic-gate  * with the License.
8*7c478bd9Sstevel@tonic-gate  *
9*7c478bd9Sstevel@tonic-gate  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10*7c478bd9Sstevel@tonic-gate  * or http://www.opensolaris.org/os/licensing.
11*7c478bd9Sstevel@tonic-gate  * See the License for the specific language governing permissions
12*7c478bd9Sstevel@tonic-gate  * and limitations under the License.
13*7c478bd9Sstevel@tonic-gate  *
14*7c478bd9Sstevel@tonic-gate  * When distributing Covered Code, include this CDDL HEADER in each
15*7c478bd9Sstevel@tonic-gate  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16*7c478bd9Sstevel@tonic-gate  * If applicable, add the following below this CDDL HEADER, with the
17*7c478bd9Sstevel@tonic-gate  * fields enclosed by brackets "[]" replaced with your own identifying
18*7c478bd9Sstevel@tonic-gate  * information: Portions Copyright [yyyy] [name of copyright owner]
19*7c478bd9Sstevel@tonic-gate  *
20*7c478bd9Sstevel@tonic-gate  * CDDL HEADER END
21*7c478bd9Sstevel@tonic-gate  */
22*7c478bd9Sstevel@tonic-gate /*	Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T	*/
23*7c478bd9Sstevel@tonic-gate /*	  All Rights Reserved  	*/
24*7c478bd9Sstevel@tonic-gate 
25*7c478bd9Sstevel@tonic-gate 
26*7c478bd9Sstevel@tonic-gate /*
27*7c478bd9Sstevel@tonic-gate  * Copyright (c) 1997, by Sun Microsystems, Inc.
28*7c478bd9Sstevel@tonic-gate  * All rights reserved.
29*7c478bd9Sstevel@tonic-gate  */
30*7c478bd9Sstevel@tonic-gate 
31*7c478bd9Sstevel@tonic-gate #pragma ident	"%Z%%M%	%I%	%E% SMI"
32*7c478bd9Sstevel@tonic-gate /*LINTLIBRARY*/
33*7c478bd9Sstevel@tonic-gate 
34*7c478bd9Sstevel@tonic-gate #include <stdio.h>
35*7c478bd9Sstevel@tonic-gate #include <string.h>
36*7c478bd9Sstevel@tonic-gate #include <sys/types.h>
37*7c478bd9Sstevel@tonic-gate #include <devmgmt.h>
38*7c478bd9Sstevel@tonic-gate #include "libadm.h"
39*7c478bd9Sstevel@tonic-gate #include <stdlib.h>
40*7c478bd9Sstevel@tonic-gate 
41*7c478bd9Sstevel@tonic-gate #define	LABELSIZ	6
42*7c478bd9Sstevel@tonic-gate #define	BELL	"\007"
43*7c478bd9Sstevel@tonic-gate 
44*7c478bd9Sstevel@tonic-gate #define	FORMFS_MSG ",\\n\\ \\ or [f] to format %s and place a filesystem on it"
45*7c478bd9Sstevel@tonic-gate #define	FORMAT_MSG ",\\n\\ \\ or [f] to format the %s"
46*7c478bd9Sstevel@tonic-gate #define	MAKEFS_MSG ",\\n\\ \\ or [m] to place a filesystem on %s"
47*7c478bd9Sstevel@tonic-gate #define	EJECT_MSG  ",\\n\\ \\ or [e] to eject the %s"
48*7c478bd9Sstevel@tonic-gate #define	UNLOAD_MSG ",\\n\\ \\ or [u] to unload/offline the %s"
49*7c478bd9Sstevel@tonic-gate #define	WLABEL_MSG ",\\n\\ \\ or [w] to write a new label on the %s"
50*7c478bd9Sstevel@tonic-gate #define	OLABEL_MSG ",\\n\\ \\ or [o] to use the current label anyway"
51*7c478bd9Sstevel@tonic-gate #define	QUIT_MSG   ",\\n\\ \\ or [q] to quit"
52*7c478bd9Sstevel@tonic-gate 
53*7c478bd9Sstevel@tonic-gate #define	ERR_ACCESS	"\n%s (%s) cannot be accessed.\n"
54*7c478bd9Sstevel@tonic-gate #define	ERR_FMT		"\nAttempt to format %s failed.\n"
55*7c478bd9Sstevel@tonic-gate #define	ERR_MKFS	"\nAttempt to place filesystem on %s failed.\n"
56*7c478bd9Sstevel@tonic-gate #define	ERR_REMOVE	"\nExecution of \"removecmd\"[%s] failed.\n"
57*7c478bd9Sstevel@tonic-gate 
58*7c478bd9Sstevel@tonic-gate static void	elabel(void);
59*7c478bd9Sstevel@tonic-gate static void	doformat(char *, char *, char *);
60*7c478bd9Sstevel@tonic-gate static void	labelerr(char *, char *);
61*7c478bd9Sstevel@tonic-gate static int	ckilabel(char *, int);
62*7c478bd9Sstevel@tonic-gate static int	insert(char *, char *, int, char *);
63*7c478bd9Sstevel@tonic-gate 
64*7c478bd9Sstevel@tonic-gate static char	*cdevice; 	/* character device name */
65*7c478bd9Sstevel@tonic-gate static char	*pname; 	/* device presentation name */
66*7c478bd9Sstevel@tonic-gate static char	*volume; 	/* volume name */
67*7c478bd9Sstevel@tonic-gate static char	origfsname[LABELSIZ+1];
68*7c478bd9Sstevel@tonic-gate static char	origvolname[LABELSIZ+1];
69*7c478bd9Sstevel@tonic-gate 
70*7c478bd9Sstevel@tonic-gate /*
71*7c478bd9Sstevel@tonic-gate  * Return:
72*7c478bd9Sstevel@tonic-gate  *	0 - okay, label matches
73*7c478bd9Sstevel@tonic-gate  *	1 - device not accessable
74*7c478bd9Sstevel@tonic-gate  *	2 - unknown device (devattr failed)
75*7c478bd9Sstevel@tonic-gate  *	3 - user selected quit
76*7c478bd9Sstevel@tonic-gate  *	4 - label does not match
77*7c478bd9Sstevel@tonic-gate  */
78*7c478bd9Sstevel@tonic-gate 
79*7c478bd9Sstevel@tonic-gate /*
80*7c478bd9Sstevel@tonic-gate  * macros from labelit to behave correctly for tape
81*7c478bd9Sstevel@tonic-gate  * is a kludge, should use devmgmt
82*7c478bd9Sstevel@tonic-gate  */
83*7c478bd9Sstevel@tonic-gate #ifdef RT
84*7c478bd9Sstevel@tonic-gate #define	IFTAPE(s) ((strncmp(s, "/dev/mt", 7) == 0) || \
85*7c478bd9Sstevel@tonic-gate (strncmp(s, "mt", 2) == 0))
86*7c478bd9Sstevel@tonic-gate #define	TAPENAMES "'/dev/mt'"
87*7c478bd9Sstevel@tonic-gate #else
88*7c478bd9Sstevel@tonic-gate #define	IFTAPE(s) ((strncmp(s, "/dev/rmt", 8) == 0) || \
89*7c478bd9Sstevel@tonic-gate (strncmp(s, "rmt", 3) == 0) || (strncmp(s, "/dev/rtp", 8) == 0) || \
90*7c478bd9Sstevel@tonic-gate (strncmp(s, "rtp", 3) == 0))
91*7c478bd9Sstevel@tonic-gate #define	TAPENAMES "'/dev/rmt' or '/dev/rtp'"
92*7c478bd9Sstevel@tonic-gate #endif
93*7c478bd9Sstevel@tonic-gate 
94*7c478bd9Sstevel@tonic-gate int
95*7c478bd9Sstevel@tonic-gate getvol(char *device, char *label, int options, char *prompt)
96*7c478bd9Sstevel@tonic-gate {
97*7c478bd9Sstevel@tonic-gate 	return (_getvol(device, label, options, prompt, NULL));
98*7c478bd9Sstevel@tonic-gate }
99*7c478bd9Sstevel@tonic-gate 
100*7c478bd9Sstevel@tonic-gate int
101*7c478bd9Sstevel@tonic-gate _getvol(char *device, char *label, int options, char *prompt, char *norewind)
102*7c478bd9Sstevel@tonic-gate {
103*7c478bd9Sstevel@tonic-gate 	FILE	*tmp;
104*7c478bd9Sstevel@tonic-gate 	char	*advice, *pt;
105*7c478bd9Sstevel@tonic-gate 	int	n, override;
106*7c478bd9Sstevel@tonic-gate 
107*7c478bd9Sstevel@tonic-gate 	cdevice = devattr(device, "cdevice");
108*7c478bd9Sstevel@tonic-gate 	if ((cdevice == NULL) || !cdevice[0]) {
109*7c478bd9Sstevel@tonic-gate 		cdevice = devattr(device, "pathname");
110*7c478bd9Sstevel@tonic-gate 		if ((cdevice == NULL) || !cdevice)
111*7c478bd9Sstevel@tonic-gate 			return (2);	/* bad device */
112*7c478bd9Sstevel@tonic-gate 	}
113*7c478bd9Sstevel@tonic-gate 
114*7c478bd9Sstevel@tonic-gate 	pname = devattr(device, "desc");
115*7c478bd9Sstevel@tonic-gate 	if (pname == NULL) {
116*7c478bd9Sstevel@tonic-gate 		pname = devattr(device, "alias");
117*7c478bd9Sstevel@tonic-gate 		if (!pname)
118*7c478bd9Sstevel@tonic-gate 			pname = device;
119*7c478bd9Sstevel@tonic-gate 	}
120*7c478bd9Sstevel@tonic-gate 
121*7c478bd9Sstevel@tonic-gate 	volume = devattr(device, "volume");
122*7c478bd9Sstevel@tonic-gate 
123*7c478bd9Sstevel@tonic-gate 	if (label) {
124*7c478bd9Sstevel@tonic-gate 		(void) strncpy(origfsname, label, LABELSIZ);
125*7c478bd9Sstevel@tonic-gate 		origfsname[LABELSIZ] = '\0';
126*7c478bd9Sstevel@tonic-gate 		if (pt = strchr(origfsname, ',')) {
127*7c478bd9Sstevel@tonic-gate 			*pt = '\0';
128*7c478bd9Sstevel@tonic-gate 		}
129*7c478bd9Sstevel@tonic-gate 		if (pt = strchr(label, ',')) {
130*7c478bd9Sstevel@tonic-gate 			(void) strncpy(origvolname, pt+1, LABELSIZ);
131*7c478bd9Sstevel@tonic-gate 			origvolname[LABELSIZ] = '\0';
132*7c478bd9Sstevel@tonic-gate 		} else
133*7c478bd9Sstevel@tonic-gate 			origvolname[0] = '\0';
134*7c478bd9Sstevel@tonic-gate 	}
135*7c478bd9Sstevel@tonic-gate 
136*7c478bd9Sstevel@tonic-gate 	override = 0;
137*7c478bd9Sstevel@tonic-gate 	for (;;) {
138*7c478bd9Sstevel@tonic-gate 		if (!(options & DM_BATCH) && volume) {
139*7c478bd9Sstevel@tonic-gate 			n = insert(device, label, options, prompt);
140*7c478bd9Sstevel@tonic-gate 			if (n < 0)
141*7c478bd9Sstevel@tonic-gate 				override++;
142*7c478bd9Sstevel@tonic-gate 			else if (n)
143*7c478bd9Sstevel@tonic-gate 				return (n);	/* input function failed */
144*7c478bd9Sstevel@tonic-gate 		}
145*7c478bd9Sstevel@tonic-gate 
146*7c478bd9Sstevel@tonic-gate 		if ((tmp = fopen(norewind ? norewind : cdevice, "r")) == NULL) {
147*7c478bd9Sstevel@tonic-gate 			/* device was not accessible */
148*7c478bd9Sstevel@tonic-gate 			if (options & DM_BATCH)
149*7c478bd9Sstevel@tonic-gate 				return (1);
150*7c478bd9Sstevel@tonic-gate 			(void) fprintf(stderr, ERR_ACCESS, pname, cdevice);
151*7c478bd9Sstevel@tonic-gate 			if ((options & DM_BATCH) || (volume == NULL))
152*7c478bd9Sstevel@tonic-gate 				return (1);
153*7c478bd9Sstevel@tonic-gate 			/* display advice on how to ready device */
154*7c478bd9Sstevel@tonic-gate 			if (advice = devattr(device, "advice"))
155*7c478bd9Sstevel@tonic-gate 				(void) puttext(stderr, advice, 0, 0);
156*7c478bd9Sstevel@tonic-gate 			continue;
157*7c478bd9Sstevel@tonic-gate 		}
158*7c478bd9Sstevel@tonic-gate 		(void) fclose(tmp);
159*7c478bd9Sstevel@tonic-gate 
160*7c478bd9Sstevel@tonic-gate 		/* check label on device */
161*7c478bd9Sstevel@tonic-gate 		if (label) {
162*7c478bd9Sstevel@tonic-gate 			if (options & DM_ELABEL)
163*7c478bd9Sstevel@tonic-gate 				elabel();
164*7c478bd9Sstevel@tonic-gate 			else {
165*7c478bd9Sstevel@tonic-gate 				/* check internal label using /etc/labelit */
166*7c478bd9Sstevel@tonic-gate 				if (ckilabel(label, override)) {
167*7c478bd9Sstevel@tonic-gate 					if ((options & DM_BATCH) ||
168*7c478bd9Sstevel@tonic-gate 					    volume == NULL)
169*7c478bd9Sstevel@tonic-gate 						return (4);
170*7c478bd9Sstevel@tonic-gate 					continue;
171*7c478bd9Sstevel@tonic-gate 				}
172*7c478bd9Sstevel@tonic-gate 			}
173*7c478bd9Sstevel@tonic-gate 		}
174*7c478bd9Sstevel@tonic-gate 		break;
175*7c478bd9Sstevel@tonic-gate 	}
176*7c478bd9Sstevel@tonic-gate 	return (0);
177*7c478bd9Sstevel@tonic-gate }
178*7c478bd9Sstevel@tonic-gate 
179*7c478bd9Sstevel@tonic-gate static int
180*7c478bd9Sstevel@tonic-gate ckilabel(char *label, int flag)
181*7c478bd9Sstevel@tonic-gate {
182*7c478bd9Sstevel@tonic-gate 	FILE	*pp;
183*7c478bd9Sstevel@tonic-gate 	char	*pt, *look, buffer[512];
184*7c478bd9Sstevel@tonic-gate 	char	fsname[LABELSIZ+1], volname[LABELSIZ+1];
185*7c478bd9Sstevel@tonic-gate 	char	*pvolname, *pfsname;
186*7c478bd9Sstevel@tonic-gate 	int	n, c;
187*7c478bd9Sstevel@tonic-gate 
188*7c478bd9Sstevel@tonic-gate 	(void) strncpy(fsname, label, LABELSIZ);
189*7c478bd9Sstevel@tonic-gate 	fsname[LABELSIZ] = '\0';
190*7c478bd9Sstevel@tonic-gate 	if (pt = strchr(fsname, ',')) {
191*7c478bd9Sstevel@tonic-gate 		*pt = '\0';
192*7c478bd9Sstevel@tonic-gate 	}
193*7c478bd9Sstevel@tonic-gate 	if (pt = strchr(label, ',')) {
194*7c478bd9Sstevel@tonic-gate 		(void) strncpy(volname, pt+1, LABELSIZ);
195*7c478bd9Sstevel@tonic-gate 		volname[LABELSIZ] = '\0';
196*7c478bd9Sstevel@tonic-gate 	} else
197*7c478bd9Sstevel@tonic-gate 		volname[0] = '\0';
198*7c478bd9Sstevel@tonic-gate 
199*7c478bd9Sstevel@tonic-gate 	(void) sprintf(buffer, "/etc/labelit %s", cdevice);
200*7c478bd9Sstevel@tonic-gate 	pp = popen(buffer, "r");
201*7c478bd9Sstevel@tonic-gate 	pt = buffer;
202*7c478bd9Sstevel@tonic-gate 	while ((c = getc(pp)) != EOF)
203*7c478bd9Sstevel@tonic-gate 		*pt++ = (char)c;
204*7c478bd9Sstevel@tonic-gate 	*pt = '\0';
205*7c478bd9Sstevel@tonic-gate 	(void) pclose(pp);
206*7c478bd9Sstevel@tonic-gate 
207*7c478bd9Sstevel@tonic-gate 	pt = buffer;
208*7c478bd9Sstevel@tonic-gate 	pfsname = pvolname = NULL;
209*7c478bd9Sstevel@tonic-gate 	look = "Current fsname: ";
210*7c478bd9Sstevel@tonic-gate 	n = (int)strlen(look);
211*7c478bd9Sstevel@tonic-gate 	while (*pt) {
212*7c478bd9Sstevel@tonic-gate 		if (strncmp(pt, look, n) == 0) {
213*7c478bd9Sstevel@tonic-gate 			*pt = '\0';
214*7c478bd9Sstevel@tonic-gate 			pt += strlen(look);
215*7c478bd9Sstevel@tonic-gate 			if (pfsname == NULL) {
216*7c478bd9Sstevel@tonic-gate 				pfsname = pt;
217*7c478bd9Sstevel@tonic-gate 				look = ", Current volname: ";
218*7c478bd9Sstevel@tonic-gate 				n = (int)strlen(look);
219*7c478bd9Sstevel@tonic-gate 			} else if (pvolname == NULL) {
220*7c478bd9Sstevel@tonic-gate 				pvolname = pt;
221*7c478bd9Sstevel@tonic-gate 				look = ", Blocks: ";
222*7c478bd9Sstevel@tonic-gate 				n = (int)strlen(look);
223*7c478bd9Sstevel@tonic-gate 			} else
224*7c478bd9Sstevel@tonic-gate 				break;
225*7c478bd9Sstevel@tonic-gate 		} else
226*7c478bd9Sstevel@tonic-gate 			pt++;
227*7c478bd9Sstevel@tonic-gate 	}
228*7c478bd9Sstevel@tonic-gate 
229*7c478bd9Sstevel@tonic-gate 	if (strcmp(fsname, pfsname) || strcmp(volname, pvolname)) {
230*7c478bd9Sstevel@tonic-gate 		/* mismatched label */
231*7c478bd9Sstevel@tonic-gate 		if (flag) {
232*7c478bd9Sstevel@tonic-gate 			(void) sprintf(label, "%s,%s", pfsname, pvolname);
233*7c478bd9Sstevel@tonic-gate 		} else {
234*7c478bd9Sstevel@tonic-gate 			labelerr(pfsname, pvolname);
235*7c478bd9Sstevel@tonic-gate 			return (1);
236*7c478bd9Sstevel@tonic-gate 		}
237*7c478bd9Sstevel@tonic-gate 	}
238*7c478bd9Sstevel@tonic-gate 	return (0);
239*7c478bd9Sstevel@tonic-gate }
240*7c478bd9Sstevel@tonic-gate 
241*7c478bd9Sstevel@tonic-gate static int
242*7c478bd9Sstevel@tonic-gate wilabel(char *label)
243*7c478bd9Sstevel@tonic-gate {
244*7c478bd9Sstevel@tonic-gate 	char	buffer[512];
245*7c478bd9Sstevel@tonic-gate 	char	fsname[LABELSIZ+1];
246*7c478bd9Sstevel@tonic-gate 	char	volname[LABELSIZ+1];
247*7c478bd9Sstevel@tonic-gate 	int	n;
248*7c478bd9Sstevel@tonic-gate 
249*7c478bd9Sstevel@tonic-gate 	if (!label || !strlen(origfsname)) {
250*7c478bd9Sstevel@tonic-gate 		if (n = ckstr(fsname, NULL, LABELSIZ, NULL, NULL, NULL,
251*7c478bd9Sstevel@tonic-gate 				"Enter text for fsname label:"))
252*7c478bd9Sstevel@tonic-gate 			return (n);
253*7c478bd9Sstevel@tonic-gate 	} else
254*7c478bd9Sstevel@tonic-gate 		(void) strcpy(fsname, origfsname);
255*7c478bd9Sstevel@tonic-gate 	if (!label || !strlen(origvolname)) {
256*7c478bd9Sstevel@tonic-gate 		if (n = ckstr(volname, NULL, LABELSIZ, NULL, NULL, NULL,
257*7c478bd9Sstevel@tonic-gate 				"Enter text for volume label:"))
258*7c478bd9Sstevel@tonic-gate 			return (n);
259*7c478bd9Sstevel@tonic-gate 	} else
260*7c478bd9Sstevel@tonic-gate 		(void) strcpy(volname, origvolname);
261*7c478bd9Sstevel@tonic-gate 
262*7c478bd9Sstevel@tonic-gate 	if (IFTAPE(cdevice)) {
263*7c478bd9Sstevel@tonic-gate 		(void) sprintf(buffer, "/etc/labelit %s \"%s\" \"%s\" -n 1>&2",
264*7c478bd9Sstevel@tonic-gate 			cdevice, fsname, volname);
265*7c478bd9Sstevel@tonic-gate 	} else {
266*7c478bd9Sstevel@tonic-gate 		(void) sprintf(buffer, "/etc/labelit %s \"%s\" \"%s\" 1>&2",
267*7c478bd9Sstevel@tonic-gate 			cdevice, fsname, volname);
268*7c478bd9Sstevel@tonic-gate 	}
269*7c478bd9Sstevel@tonic-gate 	if (system(buffer)) {
270*7c478bd9Sstevel@tonic-gate 		(void) fprintf(stderr, "\nWrite of label to %s failed.", pname);
271*7c478bd9Sstevel@tonic-gate 		return (1);
272*7c478bd9Sstevel@tonic-gate 	}
273*7c478bd9Sstevel@tonic-gate 	if (label)
274*7c478bd9Sstevel@tonic-gate 		(void) sprintf(label, "%s,%s", fsname, volname);
275*7c478bd9Sstevel@tonic-gate 	return (0);
276*7c478bd9Sstevel@tonic-gate }
277*7c478bd9Sstevel@tonic-gate 
278*7c478bd9Sstevel@tonic-gate static void
279*7c478bd9Sstevel@tonic-gate elabel(void)
280*7c478bd9Sstevel@tonic-gate {
281*7c478bd9Sstevel@tonic-gate }
282*7c478bd9Sstevel@tonic-gate 
283*7c478bd9Sstevel@tonic-gate static int
284*7c478bd9Sstevel@tonic-gate insert(char *device, char *label, int options, char *prompt)
285*7c478bd9Sstevel@tonic-gate {
286*7c478bd9Sstevel@tonic-gate 	int	n;
287*7c478bd9Sstevel@tonic-gate 	char	strval[16], prmpt[BUFSIZ];
288*7c478bd9Sstevel@tonic-gate 	char	*pt, *keyword[10];
289*7c478bd9Sstevel@tonic-gate 	char 	*fmtcmd;
290*7c478bd9Sstevel@tonic-gate 	char	*mkfscmd;
291*7c478bd9Sstevel@tonic-gate 	char	*voltxt;
292*7c478bd9Sstevel@tonic-gate 	char	*removecmd;
293*7c478bd9Sstevel@tonic-gate 	char	*dev_type;
294*7c478bd9Sstevel@tonic-gate 
295*7c478bd9Sstevel@tonic-gate 	voltxt = (volume ? volume : "volume");
296*7c478bd9Sstevel@tonic-gate 
297*7c478bd9Sstevel@tonic-gate 	fmtcmd    = devattr(device, "fmtcmd");
298*7c478bd9Sstevel@tonic-gate 	mkfscmd   = devattr(device, "mkfscmd");
299*7c478bd9Sstevel@tonic-gate 	removecmd = devattr(device, "removecmd");
300*7c478bd9Sstevel@tonic-gate 	dev_type  = devattr(device, "type");
301*7c478bd9Sstevel@tonic-gate 
302*7c478bd9Sstevel@tonic-gate 	if (prompt) {
303*7c478bd9Sstevel@tonic-gate 		(void) strcpy(prmpt, prompt);
304*7c478bd9Sstevel@tonic-gate 		for (pt = prmpt; *prompt; ) {
305*7c478bd9Sstevel@tonic-gate 			if ((*prompt == '\\') && (prompt[1] == '%'))
306*7c478bd9Sstevel@tonic-gate 				prompt++;
307*7c478bd9Sstevel@tonic-gate 			else if (*prompt == '%') {
308*7c478bd9Sstevel@tonic-gate 				switch (prompt[1]) {
309*7c478bd9Sstevel@tonic-gate 				    case 'v':
310*7c478bd9Sstevel@tonic-gate 					(void) strcpy(pt, voltxt);
311*7c478bd9Sstevel@tonic-gate 					break;
312*7c478bd9Sstevel@tonic-gate 
313*7c478bd9Sstevel@tonic-gate 				    case 'p':
314*7c478bd9Sstevel@tonic-gate 					(void) strcpy(pt, pname);
315*7c478bd9Sstevel@tonic-gate 					break;
316*7c478bd9Sstevel@tonic-gate 
317*7c478bd9Sstevel@tonic-gate 				    default:
318*7c478bd9Sstevel@tonic-gate 					*pt = '\0';
319*7c478bd9Sstevel@tonic-gate 					break;
320*7c478bd9Sstevel@tonic-gate 				}
321*7c478bd9Sstevel@tonic-gate 				pt = pt + strlen(pt);
322*7c478bd9Sstevel@tonic-gate 				prompt += 2;
323*7c478bd9Sstevel@tonic-gate 				continue;
324*7c478bd9Sstevel@tonic-gate 			}
325*7c478bd9Sstevel@tonic-gate 			*pt++ = *prompt++;
326*7c478bd9Sstevel@tonic-gate 		}
327*7c478bd9Sstevel@tonic-gate 		*pt = '\0';
328*7c478bd9Sstevel@tonic-gate 	} else {
329*7c478bd9Sstevel@tonic-gate 		(void) sprintf(prmpt, "Insert a %s into %s.", voltxt, pname);
330*7c478bd9Sstevel@tonic-gate 		if (label && (options & DM_ELABEL)) {
331*7c478bd9Sstevel@tonic-gate 			(void) strcat(prmpt, " The following external label ");
332*7c478bd9Sstevel@tonic-gate 			(void) sprintf(prmpt+strlen(prmpt),
333*7c478bd9Sstevel@tonic-gate 				" should appear on the %s:\\n\\t%s",
334*7c478bd9Sstevel@tonic-gate 				voltxt, label);
335*7c478bd9Sstevel@tonic-gate 		}
336*7c478bd9Sstevel@tonic-gate 		if (label && !(options & DM_ELABEL)) {
337*7c478bd9Sstevel@tonic-gate 			(void) sprintf(prmpt+strlen(prmpt),
338*7c478bd9Sstevel@tonic-gate 			"  The %s should be internally labeled as follows:",
339*7c478bd9Sstevel@tonic-gate 				voltxt);
340*7c478bd9Sstevel@tonic-gate 			(void) sprintf(prmpt+strlen(prmpt),
341*7c478bd9Sstevel@tonic-gate 				"\\n\\t%s\\n", label);
342*7c478bd9Sstevel@tonic-gate 		}
343*7c478bd9Sstevel@tonic-gate 	}
344*7c478bd9Sstevel@tonic-gate 
345*7c478bd9Sstevel@tonic-gate 	pt = prompt = prmpt + strlen(prmpt);
346*7c478bd9Sstevel@tonic-gate 
347*7c478bd9Sstevel@tonic-gate 	n = 0;
348*7c478bd9Sstevel@tonic-gate 	pt += sprintf(pt, "\\nType [go] when ready");
349*7c478bd9Sstevel@tonic-gate 	keyword[n++] = "go";
350*7c478bd9Sstevel@tonic-gate 
351*7c478bd9Sstevel@tonic-gate 	if (options & DM_FORMFS) {
352*7c478bd9Sstevel@tonic-gate 		if (fmtcmd && *fmtcmd && mkfscmd && *mkfscmd) {
353*7c478bd9Sstevel@tonic-gate 			pt += sprintf(pt, FORMFS_MSG, voltxt);
354*7c478bd9Sstevel@tonic-gate 			keyword[n++] = "f";
355*7c478bd9Sstevel@tonic-gate 		} else if (fmtcmd && *fmtcmd) {
356*7c478bd9Sstevel@tonic-gate 			pt += sprintf(pt, FORMAT_MSG, voltxt);
357*7c478bd9Sstevel@tonic-gate 			keyword[n++] = "f";
358*7c478bd9Sstevel@tonic-gate 		}
359*7c478bd9Sstevel@tonic-gate 		if (mkfscmd && *mkfscmd) {
360*7c478bd9Sstevel@tonic-gate 			pt += sprintf(pt, MAKEFS_MSG, voltxt);
361*7c478bd9Sstevel@tonic-gate 			keyword[n++] = "m";
362*7c478bd9Sstevel@tonic-gate 		}
363*7c478bd9Sstevel@tonic-gate 	} else if (options & DM_FORMAT) {
364*7c478bd9Sstevel@tonic-gate 		if (fmtcmd && *fmtcmd) {
365*7c478bd9Sstevel@tonic-gate 			pt += sprintf(pt, FORMAT_MSG, voltxt);
366*7c478bd9Sstevel@tonic-gate 			keyword[n++] = "f";
367*7c478bd9Sstevel@tonic-gate 		}
368*7c478bd9Sstevel@tonic-gate 	}
369*7c478bd9Sstevel@tonic-gate 	if (options & DM_WLABEL) {
370*7c478bd9Sstevel@tonic-gate 		pt += sprintf(pt, WLABEL_MSG, voltxt);
371*7c478bd9Sstevel@tonic-gate 		keyword[n++] = "w";
372*7c478bd9Sstevel@tonic-gate 	}
373*7c478bd9Sstevel@tonic-gate 	if (options & DM_OLABEL) {
374*7c478bd9Sstevel@tonic-gate 		pt += sprintf(pt, OLABEL_MSG);
375*7c478bd9Sstevel@tonic-gate 		keyword[n++] = "o";
376*7c478bd9Sstevel@tonic-gate 	}
377*7c478bd9Sstevel@tonic-gate 	if (removecmd && *removecmd && dev_type && *dev_type) {
378*7c478bd9Sstevel@tonic-gate 		if (strcmp(dev_type, "diskette") == 0) {
379*7c478bd9Sstevel@tonic-gate 			pt += sprintf(pt, EJECT_MSG, voltxt);
380*7c478bd9Sstevel@tonic-gate 			keyword[n++] = "e";
381*7c478bd9Sstevel@tonic-gate 		} else {
382*7c478bd9Sstevel@tonic-gate 			pt += sprintf(pt, UNLOAD_MSG, voltxt);
383*7c478bd9Sstevel@tonic-gate 			keyword[n++] = "u";
384*7c478bd9Sstevel@tonic-gate 		}
385*7c478bd9Sstevel@tonic-gate 	}
386*7c478bd9Sstevel@tonic-gate 	keyword[n] = NULL;
387*7c478bd9Sstevel@tonic-gate 	if (ckquit)
388*7c478bd9Sstevel@tonic-gate 		pt += sprintf(pt, QUIT_MSG);
389*7c478bd9Sstevel@tonic-gate 	*pt++ = ':';
390*7c478bd9Sstevel@tonic-gate 	*pt = '\0';
391*7c478bd9Sstevel@tonic-gate 
392*7c478bd9Sstevel@tonic-gate 	pt = prmpt;
393*7c478bd9Sstevel@tonic-gate 	(void) fprintf(stderr, BELL);
394*7c478bd9Sstevel@tonic-gate 	for (;;) {
395*7c478bd9Sstevel@tonic-gate 		if (n = ckkeywd(strval, keyword, NULL, NULL, NULL, pt))
396*7c478bd9Sstevel@tonic-gate 			return (n);
397*7c478bd9Sstevel@tonic-gate 
398*7c478bd9Sstevel@tonic-gate 		pt = prompt; /* next prompt is only partial */
399*7c478bd9Sstevel@tonic-gate 		if (*strval == 'f') {
400*7c478bd9Sstevel@tonic-gate 			if (options & DM_FORMFS)
401*7c478bd9Sstevel@tonic-gate 				doformat(voltxt, fmtcmd, mkfscmd);
402*7c478bd9Sstevel@tonic-gate 			else
403*7c478bd9Sstevel@tonic-gate 				doformat(voltxt, fmtcmd, NULL);
404*7c478bd9Sstevel@tonic-gate 			continue;
405*7c478bd9Sstevel@tonic-gate 		} else if (*strval == 'm') {
406*7c478bd9Sstevel@tonic-gate 			doformat(voltxt, NULL, mkfscmd);
407*7c478bd9Sstevel@tonic-gate 			continue;
408*7c478bd9Sstevel@tonic-gate 		} else if (*strval == 'e' || *strval == 'u') {
409*7c478bd9Sstevel@tonic-gate 			(void) doremovecmd(device, 1);
410*7c478bd9Sstevel@tonic-gate 			continue;
411*7c478bd9Sstevel@tonic-gate 		} else if (*strval == 'w') {
412*7c478bd9Sstevel@tonic-gate 			(void) wilabel(label);
413*7c478bd9Sstevel@tonic-gate 			continue;
414*7c478bd9Sstevel@tonic-gate 		} else if (*strval == 'o')
415*7c478bd9Sstevel@tonic-gate 			return (-1);
416*7c478bd9Sstevel@tonic-gate 		break;
417*7c478bd9Sstevel@tonic-gate 	}
418*7c478bd9Sstevel@tonic-gate 	return (0);
419*7c478bd9Sstevel@tonic-gate }
420*7c478bd9Sstevel@tonic-gate 
421*7c478bd9Sstevel@tonic-gate static void
422*7c478bd9Sstevel@tonic-gate doformat(char *voltxt, char *fmtcmd, char *mkfscmd)
423*7c478bd9Sstevel@tonic-gate {
424*7c478bd9Sstevel@tonic-gate 	char	buffer[512];
425*7c478bd9Sstevel@tonic-gate 
426*7c478bd9Sstevel@tonic-gate 	if (fmtcmd && *fmtcmd) {
427*7c478bd9Sstevel@tonic-gate 		(void) fprintf(stderr, "\t[%s]\n", fmtcmd);
428*7c478bd9Sstevel@tonic-gate 		(void) sprintf(buffer, "(%s) 1>&2", fmtcmd);
429*7c478bd9Sstevel@tonic-gate 		if (system(buffer)) {
430*7c478bd9Sstevel@tonic-gate 			(void) fprintf(stderr, ERR_FMT, voltxt);
431*7c478bd9Sstevel@tonic-gate 			return;
432*7c478bd9Sstevel@tonic-gate 		}
433*7c478bd9Sstevel@tonic-gate 	}
434*7c478bd9Sstevel@tonic-gate 	if (mkfscmd && *mkfscmd) {
435*7c478bd9Sstevel@tonic-gate 		(void) fprintf(stderr, "\t[%s]\n", mkfscmd);
436*7c478bd9Sstevel@tonic-gate 		(void) sprintf(buffer, "(%s) 1>&2", mkfscmd);
437*7c478bd9Sstevel@tonic-gate 		if (system(buffer)) {
438*7c478bd9Sstevel@tonic-gate 			(void) fprintf(stderr, ERR_MKFS, voltxt);
439*7c478bd9Sstevel@tonic-gate 			return;
440*7c478bd9Sstevel@tonic-gate 		}
441*7c478bd9Sstevel@tonic-gate 	}
442*7c478bd9Sstevel@tonic-gate }
443*7c478bd9Sstevel@tonic-gate 
444*7c478bd9Sstevel@tonic-gate void
445*7c478bd9Sstevel@tonic-gate doremovecmd(char *device, int echo)
446*7c478bd9Sstevel@tonic-gate {
447*7c478bd9Sstevel@tonic-gate 	char 	*removecmd;
448*7c478bd9Sstevel@tonic-gate 	char	buffer[512];
449*7c478bd9Sstevel@tonic-gate 
450*7c478bd9Sstevel@tonic-gate 	if (device && *device) {
451*7c478bd9Sstevel@tonic-gate 		removecmd = devattr(device, "removecmd");
452*7c478bd9Sstevel@tonic-gate 		if (removecmd && *removecmd) {
453*7c478bd9Sstevel@tonic-gate 			if (echo)
454*7c478bd9Sstevel@tonic-gate 				(void) fprintf(stderr, "\t[%s]\n", removecmd);
455*7c478bd9Sstevel@tonic-gate 			(void) sprintf(buffer, "(%s) 1>&2", removecmd);
456*7c478bd9Sstevel@tonic-gate 			if (system(buffer)) {
457*7c478bd9Sstevel@tonic-gate 				if (echo)
458*7c478bd9Sstevel@tonic-gate 					(void) fprintf(stderr, ERR_REMOVE,
459*7c478bd9Sstevel@tonic-gate 					removecmd);
460*7c478bd9Sstevel@tonic-gate 				return;
461*7c478bd9Sstevel@tonic-gate 			}
462*7c478bd9Sstevel@tonic-gate 		}
463*7c478bd9Sstevel@tonic-gate 	}
464*7c478bd9Sstevel@tonic-gate }
465*7c478bd9Sstevel@tonic-gate 
466*7c478bd9Sstevel@tonic-gate static void
467*7c478bd9Sstevel@tonic-gate labelerr(char *fsname, char *volname)
468*7c478bd9Sstevel@tonic-gate {
469*7c478bd9Sstevel@tonic-gate 	(void) fprintf(stderr, "\nLabel incorrect.\n");
470*7c478bd9Sstevel@tonic-gate 	if (volume)
471*7c478bd9Sstevel@tonic-gate 		(void) fprintf(stderr,
472*7c478bd9Sstevel@tonic-gate 			"The internal label on the inserted %s is\n", volume);
473*7c478bd9Sstevel@tonic-gate 	else
474*7c478bd9Sstevel@tonic-gate 		(void) fprintf(stderr, "The internal label for %s is", pname);
475*7c478bd9Sstevel@tonic-gate 	(void) fprintf(stderr, "\t%s,%s\n", fsname, volname);
476*7c478bd9Sstevel@tonic-gate }
477