1/*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22/*
23 * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved.
24 * Copyright 2011 Nexenta Systems, Inc. All rights reserved.
25 * Copyright (c) 2013 by Delphix. All rights reserved.
26 * Copyright (c) 2012 by Frederik Wessels. All rights reserved.
27 * Copyright (c) 2012 Martin Matuska <mm@FreeBSD.org>. All rights reserved.
28 */
29
30#include <solaris.h>
31#include <assert.h>
32#include <ctype.h>
33#include <dirent.h>
34#include <errno.h>
35#include <fcntl.h>
36#include <libgen.h>
37#include <libintl.h>
38#include <libuutil.h>
39#include <locale.h>
40#include <stdio.h>
41#include <stdlib.h>
42#include <string.h>
43#include <strings.h>
44#include <unistd.h>
45#include <priv.h>
46#include <pwd.h>
47#include <zone.h>
48#include <sys/time.h>
49#include <zfs_prop.h>
50#include <sys/fs/zfs.h>
51#include <sys/stat.h>
52
53#include <libzfs.h>
54
55#include "zpool_util.h"
56#include "zfs_comutil.h"
57#include "zfeature_common.h"
58
59#include "statcommon.h"
60
61static int zpool_do_create(int, char **);
62static int zpool_do_destroy(int, char **);
63
64static int zpool_do_add(int, char **);
65static int zpool_do_remove(int, char **);
66static int zpool_do_labelclear(int, char **);
67
68static int zpool_do_list(int, char **);
69static int zpool_do_iostat(int, char **);
70static int zpool_do_status(int, char **);
71
72static int zpool_do_online(int, char **);
73static int zpool_do_offline(int, char **);
74static int zpool_do_clear(int, char **);
75static int zpool_do_reopen(int, char **);
76
77static int zpool_do_reguid(int, char **);
78
79static int zpool_do_attach(int, char **);
80static int zpool_do_detach(int, char **);
81static int zpool_do_replace(int, char **);
82static int zpool_do_split(int, char **);
83
84static int zpool_do_scrub(int, char **);
85
86static int zpool_do_import(int, char **);
87static int zpool_do_export(int, char **);
88
89static int zpool_do_upgrade(int, char **);
90
91static int zpool_do_history(int, char **);
92
93static int zpool_do_get(int, char **);
94static int zpool_do_set(int, char **);
95
96/*
97 * These libumem hooks provide a reasonable set of defaults for the allocator's
98 * debugging facilities.
99 */
100
101#ifdef DEBUG
102const char *
103_umem_debug_init(void)
104{
105	return ("default,verbose"); /* $UMEM_DEBUG setting */
106}
107
108const char *
109_umem_logging_init(void)
110{
111	return ("fail,contents"); /* $UMEM_LOGGING setting */
112}
113#endif
114
115typedef enum {
116	HELP_ADD,
117	HELP_ATTACH,
118	HELP_CLEAR,
119	HELP_CREATE,
120	HELP_DESTROY,
121	HELP_DETACH,
122	HELP_EXPORT,
123	HELP_HISTORY,
124	HELP_IMPORT,
125	HELP_IOSTAT,
126	HELP_LABELCLEAR,
127	HELP_LIST,
128	HELP_OFFLINE,
129	HELP_ONLINE,
130	HELP_REPLACE,
131	HELP_REMOVE,
132	HELP_SCRUB,
133	HELP_STATUS,
134	HELP_UPGRADE,
135	HELP_GET,
136	HELP_SET,
137	HELP_SPLIT,
138	HELP_REGUID,
139	HELP_REOPEN
140} zpool_help_t;
141
142
143typedef struct zpool_command {
144	const char	*name;
145	int		(*func)(int, char **);
146	zpool_help_t	usage;
147} zpool_command_t;
148
149/*
150 * Master command table.  Each ZFS command has a name, associated function, and
151 * usage message.  The usage messages need to be internationalized, so we have
152 * to have a function to return the usage message based on a command index.
153 *
154 * These commands are organized according to how they are displayed in the usage
155 * message.  An empty command (one with a NULL name) indicates an empty line in
156 * the generic usage message.
157 */
158static zpool_command_t command_table[] = {
159	{ "create",	zpool_do_create,	HELP_CREATE		},
160	{ "destroy",	zpool_do_destroy,	HELP_DESTROY		},
161	{ NULL },
162	{ "add",	zpool_do_add,		HELP_ADD		},
163	{ "remove",	zpool_do_remove,	HELP_REMOVE		},
164	{ NULL },
165	{ "labelclear",	zpool_do_labelclear,	HELP_LABELCLEAR		},
166	{ NULL },
167	{ "list",	zpool_do_list,		HELP_LIST		},
168	{ "iostat",	zpool_do_iostat,	HELP_IOSTAT		},
169	{ "status",	zpool_do_status,	HELP_STATUS		},
170	{ NULL },
171	{ "online",	zpool_do_online,	HELP_ONLINE		},
172	{ "offline",	zpool_do_offline,	HELP_OFFLINE		},
173	{ "clear",	zpool_do_clear,		HELP_CLEAR		},
174	{ "reopen",	zpool_do_reopen,	HELP_REOPEN		},
175	{ NULL },
176	{ "attach",	zpool_do_attach,	HELP_ATTACH		},
177	{ "detach",	zpool_do_detach,	HELP_DETACH		},
178	{ "replace",	zpool_do_replace,	HELP_REPLACE		},
179	{ "split",	zpool_do_split,		HELP_SPLIT		},
180	{ NULL },
181	{ "scrub",	zpool_do_scrub,		HELP_SCRUB		},
182	{ NULL },
183	{ "import",	zpool_do_import,	HELP_IMPORT		},
184	{ "export",	zpool_do_export,	HELP_EXPORT		},
185	{ "upgrade",	zpool_do_upgrade,	HELP_UPGRADE		},
186	{ "reguid",	zpool_do_reguid,	HELP_REGUID		},
187	{ NULL },
188	{ "history",	zpool_do_history,	HELP_HISTORY		},
189	{ "get",	zpool_do_get,		HELP_GET		},
190	{ "set",	zpool_do_set,		HELP_SET		},
191};
192
193#define	NCOMMAND	(sizeof (command_table) / sizeof (command_table[0]))
194
195static zpool_command_t *current_command;
196static char history_str[HIS_MAX_RECORD_LEN];
197static boolean_t log_history = B_TRUE;
198static uint_t timestamp_fmt = NODATE;
199
200static const char *
201get_usage(zpool_help_t idx) {
202	switch (idx) {
203	case HELP_ADD:
204		return (gettext("\tadd [-fn] <pool> <vdev> ...\n"));
205	case HELP_ATTACH:
206		return (gettext("\tattach [-f] <pool> <device> "
207		    "<new-device>\n"));
208	case HELP_CLEAR:
209		return (gettext("\tclear [-nF] <pool> [device]\n"));
210	case HELP_CREATE:
211		return (gettext("\tcreate [-fnd] [-o property=value] ... \n"
212		    "\t    [-O file-system-property=value] ... \n"
213		    "\t    [-m mountpoint] [-R root] <pool> <vdev> ...\n"));
214	case HELP_DESTROY:
215		return (gettext("\tdestroy [-f] <pool>\n"));
216	case HELP_DETACH:
217		return (gettext("\tdetach <pool> <device>\n"));
218	case HELP_EXPORT:
219		return (gettext("\texport [-f] <pool> ...\n"));
220	case HELP_HISTORY:
221		return (gettext("\thistory [-il] [<pool>] ...\n"));
222	case HELP_IMPORT:
223		return (gettext("\timport [-d dir] [-D]\n"
224		    "\timport [-d dir | -c cachefile] [-F [-n]] <pool | id>\n"
225		    "\timport [-o mntopts] [-o property=value] ... \n"
226		    "\t    [-d dir | -c cachefile] [-D] [-f] [-m] [-N] "
227		    "[-R root] [-F [-n]] -a\n"
228		    "\timport [-o mntopts] [-o property=value] ... \n"
229		    "\t    [-d dir | -c cachefile] [-D] [-f] [-m] [-N] "
230		    "[-R root] [-F [-n]]\n"
231		    "\t    <pool | id> [newpool]\n"));
232	case HELP_IOSTAT:
233		return (gettext("\tiostat [-v] [-T d|u] [pool] ... [interval "
234		    "[count]]\n"));
235	case HELP_LABELCLEAR:
236		return (gettext("\tlabelclear [-f] <vdev>\n"));
237	case HELP_LIST:
238		return (gettext("\tlist [-Hpv] [-o property[,...]] "
239		    "[-T d|u] [pool] ... [interval [count]]\n"));
240	case HELP_OFFLINE:
241		return (gettext("\toffline [-t] <pool> <device> ...\n"));
242	case HELP_ONLINE:
243		return (gettext("\tonline [-e] <pool> <device> ...\n"));
244	case HELP_REPLACE:
245		return (gettext("\treplace [-f] <pool> <device> "
246		    "[new-device]\n"));
247	case HELP_REMOVE:
248		return (gettext("\tremove <pool> <device> ...\n"));
249	case HELP_REOPEN:
250		return (gettext("\treopen <pool>\n"));
251	case HELP_SCRUB:
252		return (gettext("\tscrub [-s] <pool> ...\n"));
253	case HELP_STATUS:
254		return (gettext("\tstatus [-vx] [-T d|u] [pool] ... [interval "
255		    "[count]]\n"));
256	case HELP_UPGRADE:
257		return (gettext("\tupgrade [-v]\n"
258		    "\tupgrade [-V version] <-a | pool ...>\n"));
259	case HELP_GET:
260		return (gettext("\tget [-Hp] [-o \"all\" | field[,...]] "
261		    "<\"all\" | property[,...]> <pool> ...\n"));
262	case HELP_SET:
263		return (gettext("\tset <property=value> <pool> \n"));
264	case HELP_SPLIT:
265		return (gettext("\tsplit [-n] [-R altroot] [-o mntopts]\n"
266		    "\t    [-o property=value] <pool> <newpool> "
267		    "[<device> ...]\n"));
268	case HELP_REGUID:
269		return (gettext("\treguid <pool>\n"));
270	}
271
272	abort();
273	/* NOTREACHED */
274}
275
276
277/*
278 * Callback routine that will print out a pool property value.
279 */
280static int
281print_prop_cb(int prop, void *cb)
282{
283	FILE *fp = cb;
284
285	(void) fprintf(fp, "\t%-15s  ", zpool_prop_to_name(prop));
286
287	if (zpool_prop_readonly(prop))
288		(void) fprintf(fp, "  NO   ");
289	else
290		(void) fprintf(fp, " YES   ");
291
292	if (zpool_prop_values(prop) == NULL)
293		(void) fprintf(fp, "-\n");
294	else
295		(void) fprintf(fp, "%s\n", zpool_prop_values(prop));
296
297	return (ZPROP_CONT);
298}
299
300/*
301 * Display usage message.  If we're inside a command, display only the usage for
302 * that command.  Otherwise, iterate over the entire command table and display
303 * a complete usage message.
304 */
305void
306usage(boolean_t requested)
307{
308	FILE *fp = requested ? stdout : stderr;
309
310	if (current_command == NULL) {
311		int i;
312
313		(void) fprintf(fp, gettext("usage: zpool command args ...\n"));
314		(void) fprintf(fp,
315		    gettext("where 'command' is one of the following:\n\n"));
316
317		for (i = 0; i < NCOMMAND; i++) {
318			if (command_table[i].name == NULL)
319				(void) fprintf(fp, "\n");
320			else
321				(void) fprintf(fp, "%s",
322				    get_usage(command_table[i].usage));
323		}
324	} else {
325		(void) fprintf(fp, gettext("usage:\n"));
326		(void) fprintf(fp, "%s", get_usage(current_command->usage));
327	}
328
329	if (current_command != NULL &&
330	    ((strcmp(current_command->name, "set") == 0) ||
331	    (strcmp(current_command->name, "get") == 0) ||
332	    (strcmp(current_command->name, "list") == 0))) {
333
334		(void) fprintf(fp,
335		    gettext("\nthe following properties are supported:\n"));
336
337		(void) fprintf(fp, "\n\t%-15s  %s   %s\n\n",
338		    "PROPERTY", "EDIT", "VALUES");
339
340		/* Iterate over all properties */
341		(void) zprop_iter(print_prop_cb, fp, B_FALSE, B_TRUE,
342		    ZFS_TYPE_POOL);
343
344		(void) fprintf(fp, "\t%-15s   ", "feature@...");
345		(void) fprintf(fp, "YES   disabled | enabled | active\n");
346
347		(void) fprintf(fp, gettext("\nThe feature@ properties must be "
348		    "appended with a feature name.\nSee zpool-features(7).\n"));
349	}
350
351	/*
352	 * See comments at end of main().
353	 */
354	if (getenv("ZFS_ABORT") != NULL) {
355		(void) printf("dumping core by request\n");
356		abort();
357	}
358
359	exit(requested ? 0 : 2);
360}
361
362void
363print_vdev_tree(zpool_handle_t *zhp, const char *name, nvlist_t *nv, int indent,
364    boolean_t print_logs)
365{
366	nvlist_t **child;
367	uint_t c, children;
368	char *vname;
369
370	if (name != NULL)
371		(void) printf("\t%*s%s\n", indent, "", name);
372
373	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
374	    &child, &children) != 0)
375		return;
376
377	for (c = 0; c < children; c++) {
378		uint64_t is_log = B_FALSE;
379
380		(void) nvlist_lookup_uint64(child[c], ZPOOL_CONFIG_IS_LOG,
381		    &is_log);
382		if ((is_log && !print_logs) || (!is_log && print_logs))
383			continue;
384
385		vname = zpool_vdev_name(g_zfs, zhp, child[c], B_FALSE);
386		print_vdev_tree(zhp, vname, child[c], indent + 2,
387		    B_FALSE);
388		free(vname);
389	}
390}
391
392static boolean_t
393prop_list_contains_feature(nvlist_t *proplist)
394{
395	nvpair_t *nvp;
396	for (nvp = nvlist_next_nvpair(proplist, NULL); NULL != nvp;
397	    nvp = nvlist_next_nvpair(proplist, nvp)) {
398		if (zpool_prop_feature(nvpair_name(nvp)))
399			return (B_TRUE);
400	}
401	return (B_FALSE);
402}
403
404/*
405 * Add a property pair (name, string-value) into a property nvlist.
406 */
407static int
408add_prop_list(const char *propname, char *propval, nvlist_t **props,
409    boolean_t poolprop)
410{
411	zpool_prop_t prop = ZPROP_INVAL;
412	zfs_prop_t fprop;
413	nvlist_t *proplist;
414	const char *normnm;
415	char *strval;
416
417	if (*props == NULL &&
418	    nvlist_alloc(props, NV_UNIQUE_NAME, 0) != 0) {
419		(void) fprintf(stderr,
420		    gettext("internal error: out of memory\n"));
421		return (1);
422	}
423
424	proplist = *props;
425
426	if (poolprop) {
427		const char *vname = zpool_prop_to_name(ZPOOL_PROP_VERSION);
428
429		if ((prop = zpool_name_to_prop(propname)) == ZPROP_INVAL &&
430		    !zpool_prop_feature(propname)) {
431			(void) fprintf(stderr, gettext("property '%s' is "
432			    "not a valid pool property\n"), propname);
433			return (2);
434		}
435
436		/*
437		 * feature@ properties and version should not be specified
438		 * at the same time.
439		 */
440		if ((prop == ZPROP_INVAL && zpool_prop_feature(propname) &&
441		    nvlist_exists(proplist, vname)) ||
442		    (prop == ZPOOL_PROP_VERSION &&
443		    prop_list_contains_feature(proplist))) {
444			(void) fprintf(stderr, gettext("'feature@' and "
445			    "'version' properties cannot be specified "
446			    "together\n"));
447			return (2);
448		}
449
450
451		if (zpool_prop_feature(propname))
452			normnm = propname;
453		else
454			normnm = zpool_prop_to_name(prop);
455	} else {
456		if ((fprop = zfs_name_to_prop(propname)) != ZPROP_INVAL) {
457			normnm = zfs_prop_to_name(fprop);
458		} else {
459			normnm = propname;
460		}
461	}
462
463	if (nvlist_lookup_string(proplist, normnm, &strval) == 0 &&
464	    prop != ZPOOL_PROP_CACHEFILE) {
465		(void) fprintf(stderr, gettext("property '%s' "
466		    "specified multiple times\n"), propname);
467		return (2);
468	}
469
470	if (nvlist_add_string(proplist, normnm, propval) != 0) {
471		(void) fprintf(stderr, gettext("internal "
472		    "error: out of memory\n"));
473		return (1);
474	}
475
476	return (0);
477}
478
479/*
480 * zpool add [-fn] <pool> <vdev> ...
481 *
482 *	-f	Force addition of devices, even if they appear in use
483 *	-n	Do not add the devices, but display the resulting layout if
484 *		they were to be added.
485 *
486 * Adds the given vdevs to 'pool'.  As with create, the bulk of this work is
487 * handled by get_vdev_spec(), which constructs the nvlist needed to pass to
488 * libzfs.
489 */
490int
491zpool_do_add(int argc, char **argv)
492{
493	boolean_t force = B_FALSE;
494	boolean_t dryrun = B_FALSE;
495	int c;
496	nvlist_t *nvroot;
497	char *poolname;
498	int ret;
499	zpool_handle_t *zhp;
500	nvlist_t *config;
501
502	/* check options */
503	while ((c = getopt(argc, argv, "fn")) != -1) {
504		switch (c) {
505		case 'f':
506			force = B_TRUE;
507			break;
508		case 'n':
509			dryrun = B_TRUE;
510			break;
511		case '?':
512			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
513			    optopt);
514			usage(B_FALSE);
515		}
516	}
517
518	argc -= optind;
519	argv += optind;
520
521	/* get pool name and check number of arguments */
522	if (argc < 1) {
523		(void) fprintf(stderr, gettext("missing pool name argument\n"));
524		usage(B_FALSE);
525	}
526	if (argc < 2) {
527		(void) fprintf(stderr, gettext("missing vdev specification\n"));
528		usage(B_FALSE);
529	}
530
531	poolname = argv[0];
532
533	argc--;
534	argv++;
535
536	if ((zhp = zpool_open(g_zfs, poolname)) == NULL)
537		return (1);
538
539	if ((config = zpool_get_config(zhp, NULL)) == NULL) {
540		(void) fprintf(stderr, gettext("pool '%s' is unavailable\n"),
541		    poolname);
542		zpool_close(zhp);
543		return (1);
544	}
545
546	/* pass off to get_vdev_spec for processing */
547	nvroot = make_root_vdev(zhp, force, !force, B_FALSE, dryrun,
548	    argc, argv);
549	if (nvroot == NULL) {
550		zpool_close(zhp);
551		return (1);
552	}
553
554	if (dryrun) {
555		nvlist_t *poolnvroot;
556
557		verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE,
558		    &poolnvroot) == 0);
559
560		(void) printf(gettext("would update '%s' to the following "
561		    "configuration:\n"), zpool_get_name(zhp));
562
563		/* print original main pool and new tree */
564		print_vdev_tree(zhp, poolname, poolnvroot, 0, B_FALSE);
565		print_vdev_tree(zhp, NULL, nvroot, 0, B_FALSE);
566
567		/* Do the same for the logs */
568		if (num_logs(poolnvroot) > 0) {
569			print_vdev_tree(zhp, "logs", poolnvroot, 0, B_TRUE);
570			print_vdev_tree(zhp, NULL, nvroot, 0, B_TRUE);
571		} else if (num_logs(nvroot) > 0) {
572			print_vdev_tree(zhp, "logs", nvroot, 0, B_TRUE);
573		}
574
575		ret = 0;
576	} else {
577		ret = (zpool_add(zhp, nvroot) != 0);
578	}
579
580	nvlist_free(nvroot);
581	zpool_close(zhp);
582
583	return (ret);
584}
585
586/*
587 * zpool remove  <pool> <vdev> ...
588 *
589 * Removes the given vdev from the pool.  Currently, this supports removing
590 * spares, cache, and log devices from the pool.
591 */
592int
593zpool_do_remove(int argc, char **argv)
594{
595	char *poolname;
596	int i, ret = 0;
597	zpool_handle_t *zhp;
598
599	argc--;
600	argv++;
601
602	/* get pool name and check number of arguments */
603	if (argc < 1) {
604		(void) fprintf(stderr, gettext("missing pool name argument\n"));
605		usage(B_FALSE);
606	}
607	if (argc < 2) {
608		(void) fprintf(stderr, gettext("missing device\n"));
609		usage(B_FALSE);
610	}
611
612	poolname = argv[0];
613
614	if ((zhp = zpool_open(g_zfs, poolname)) == NULL)
615		return (1);
616
617	for (i = 1; i < argc; i++) {
618		if (zpool_vdev_remove(zhp, argv[i]) != 0)
619			ret = 1;
620	}
621
622	return (ret);
623}
624
625/*
626 * zpool labelclear <vdev>
627 *
628 * Verifies that the vdev is not active and zeros out the label information
629 * on the device.
630 */
631int
632zpool_do_labelclear(int argc, char **argv)
633{
634	char *vdev, *name;
635	int c, fd = -1, ret = 0;
636	pool_state_t state;
637	boolean_t inuse = B_FALSE;
638	boolean_t force = B_FALSE;
639
640	/* check options */
641	while ((c = getopt(argc, argv, "f")) != -1) {
642		switch (c) {
643		case 'f':
644			force = B_TRUE;
645			break;
646		default:
647			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
648			    optopt);
649			usage(B_FALSE);
650		}
651	}
652
653	argc -= optind;
654	argv += optind;
655
656	/* get vdev name */
657	if (argc < 1) {
658		(void) fprintf(stderr, gettext("missing vdev device name\n"));
659		usage(B_FALSE);
660	}
661
662	vdev = argv[0];
663	if ((fd = open(vdev, O_RDWR)) < 0) {
664		(void) fprintf(stderr, gettext("Unable to open %s\n"), vdev);
665		return (B_FALSE);
666	}
667
668	name = NULL;
669	if (zpool_in_use(g_zfs, fd, &state, &name, &inuse) != 0) {
670		if (force)
671			goto wipe_label;
672
673		(void) fprintf(stderr,
674		    gettext("Unable to determine pool state for %s\n"
675		    "Use -f to force the clearing any label data\n"), vdev);
676
677		return (1);
678	}
679
680	if (inuse) {
681		switch (state) {
682		default:
683		case POOL_STATE_ACTIVE:
684		case POOL_STATE_SPARE:
685		case POOL_STATE_L2CACHE:
686			(void) fprintf(stderr,
687gettext("labelclear operation failed.\n"
688	"\tVdev %s is a member (%s), of pool \"%s\".\n"
689	"\tTo remove label information from this device, export or destroy\n"
690	"\tthe pool, or remove %s from the configuration of this pool\n"
691	"\tand retry the labelclear operation\n"),
692			    vdev, zpool_pool_state_to_name(state), name, vdev);
693			ret = 1;
694			goto errout;
695
696		case POOL_STATE_EXPORTED:
697			if (force)
698				break;
699
700			(void) fprintf(stderr,
701gettext("labelclear operation failed.\n"
702	"\tVdev %s is a member of the exported pool \"%s\".\n"
703	"\tUse \"zpool labelclear -f %s\" to force the removal of label\n"
704	"\tinformation.\n"),
705			    vdev, name, vdev);
706			ret = 1;
707			goto errout;
708
709		case POOL_STATE_POTENTIALLY_ACTIVE:
710			if (force)
711				break;
712
713			(void) fprintf(stderr,
714gettext("labelclear operation failed.\n"
715	"\tVdev %s is a member of the pool \"%s\".\n"
716	"\tThis pool is unknown to this system, but may be active on\n"
717	"\tanother system. Use \'zpool labelclear -f %s\' to force the\n"
718	"\tremoval of label information.\n"),
719			    vdev, name, vdev);
720			ret = 1;
721			goto errout;
722
723		case POOL_STATE_DESTROYED:
724			/* inuse should never be set for a destoryed pool... */
725			break;
726		}
727	}
728
729wipe_label:
730	if (zpool_clear_label(fd) != 0) {
731		(void) fprintf(stderr,
732		    gettext("Label clear failed on vdev %s\n"), vdev);
733		ret = 1;
734	}
735
736errout:
737	close(fd);
738	if (name != NULL)
739		free(name);
740
741	return (ret);
742}
743
744/*
745 * zpool create [-fnd] [-o property=value] ...
746 *		[-O file-system-property=value] ...
747 *		[-R root] [-m mountpoint] <pool> <dev> ...
748 *
749 *	-f	Force creation, even if devices appear in use
750 *	-n	Do not create the pool, but display the resulting layout if it
751 *		were to be created.
752 *      -R	Create a pool under an alternate root
753 *      -m	Set default mountpoint for the root dataset.  By default it's
754 *		'/<pool>'
755 *	-o	Set property=value.
756 *	-d	Don't automatically enable all supported pool features
757 *		(individual features can be enabled with -o).
758 *	-O	Set fsproperty=value in the pool's root file system
759 *
760 * Creates the named pool according to the given vdev specification.  The
761 * bulk of the vdev processing is done in get_vdev_spec() in zpool_vdev.c.  Once
762 * we get the nvlist back from get_vdev_spec(), we either print out the contents
763 * (if '-n' was specified), or pass it to libzfs to do the creation.
764 */
765int
766zpool_do_create(int argc, char **argv)
767{
768	boolean_t force = B_FALSE;
769	boolean_t dryrun = B_FALSE;
770	boolean_t enable_all_pool_feat = B_TRUE;
771	int c;
772	nvlist_t *nvroot = NULL;
773	char *poolname;
774	int ret = 1;
775	char *altroot = NULL;
776	char *mountpoint = NULL;
777	nvlist_t *fsprops = NULL;
778	nvlist_t *props = NULL;
779	char *propval;
780
781	/* check options */
782	while ((c = getopt(argc, argv, ":fndR:m:o:O:")) != -1) {
783		switch (c) {
784		case 'f':
785			force = B_TRUE;
786			break;
787		case 'n':
788			dryrun = B_TRUE;
789			break;
790		case 'd':
791			enable_all_pool_feat = B_FALSE;
792			break;
793		case 'R':
794			altroot = optarg;
795			if (add_prop_list(zpool_prop_to_name(
796			    ZPOOL_PROP_ALTROOT), optarg, &props, B_TRUE))
797				goto errout;
798			if (nvlist_lookup_string(props,
799			    zpool_prop_to_name(ZPOOL_PROP_CACHEFILE),
800			    &propval) == 0)
801				break;
802			if (add_prop_list(zpool_prop_to_name(
803			    ZPOOL_PROP_CACHEFILE), "none", &props, B_TRUE))
804				goto errout;
805			break;
806		case 'm':
807			/* Equivalent to -O mountpoint=optarg */
808			mountpoint = optarg;
809			break;
810		case 'o':
811			if ((propval = strchr(optarg, '=')) == NULL) {
812				(void) fprintf(stderr, gettext("missing "
813				    "'=' for -o option\n"));
814				goto errout;
815			}
816			*propval = '\0';
817			propval++;
818
819			if (add_prop_list(optarg, propval, &props, B_TRUE))
820				goto errout;
821
822			/*
823			 * If the user is creating a pool that doesn't support
824			 * feature flags, don't enable any features.
825			 */
826			if (zpool_name_to_prop(optarg) == ZPOOL_PROP_VERSION) {
827				char *end;
828				u_longlong_t ver;
829
830				ver = strtoull(propval, &end, 10);
831				if (*end == '\0' &&
832				    ver < SPA_VERSION_FEATURES) {
833					enable_all_pool_feat = B_FALSE;
834				}
835			}
836			break;
837		case 'O':
838			if ((propval = strchr(optarg, '=')) == NULL) {
839				(void) fprintf(stderr, gettext("missing "
840				    "'=' for -O option\n"));
841				goto errout;
842			}
843			*propval = '\0';
844			propval++;
845
846			/*
847			 * Mountpoints are checked and then added later.
848			 * Uniquely among properties, they can be specified
849			 * more than once, to avoid conflict with -m.
850			 */
851			if (0 == strcmp(optarg,
852			    zfs_prop_to_name(ZFS_PROP_MOUNTPOINT))) {
853				mountpoint = propval;
854			} else if (add_prop_list(optarg, propval, &fsprops,
855			    B_FALSE)) {
856				goto errout;
857			}
858			break;
859		case ':':
860			(void) fprintf(stderr, gettext("missing argument for "
861			    "'%c' option\n"), optopt);
862			goto badusage;
863		case '?':
864			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
865			    optopt);
866			goto badusage;
867		}
868	}
869
870	argc -= optind;
871	argv += optind;
872
873	/* get pool name and check number of arguments */
874	if (argc < 1) {
875		(void) fprintf(stderr, gettext("missing pool name argument\n"));
876		goto badusage;
877	}
878	if (argc < 2) {
879		(void) fprintf(stderr, gettext("missing vdev specification\n"));
880		goto badusage;
881	}
882
883	poolname = argv[0];
884
885	/*
886	 * As a special case, check for use of '/' in the name, and direct the
887	 * user to use 'zfs create' instead.
888	 */
889	if (strchr(poolname, '/') != NULL) {
890		(void) fprintf(stderr, gettext("cannot create '%s': invalid "
891		    "character '/' in pool name\n"), poolname);
892		(void) fprintf(stderr, gettext("use 'zfs create' to "
893		    "create a dataset\n"));
894		goto errout;
895	}
896
897	/* pass off to get_vdev_spec for bulk processing */
898	nvroot = make_root_vdev(NULL, force, !force, B_FALSE, dryrun,
899	    argc - 1, argv + 1);
900	if (nvroot == NULL)
901		goto errout;
902
903	/* make_root_vdev() allows 0 toplevel children if there are spares */
904	if (!zfs_allocatable_devs(nvroot)) {
905		(void) fprintf(stderr, gettext("invalid vdev "
906		    "specification: at least one toplevel vdev must be "
907		    "specified\n"));
908		goto errout;
909	}
910
911	if (altroot != NULL && altroot[0] != '/') {
912		(void) fprintf(stderr, gettext("invalid alternate root '%s': "
913		    "must be an absolute path\n"), altroot);
914		goto errout;
915	}
916
917	/*
918	 * Check the validity of the mountpoint and direct the user to use the
919	 * '-m' mountpoint option if it looks like its in use.
920	 */
921	if (mountpoint == NULL ||
922	    (strcmp(mountpoint, ZFS_MOUNTPOINT_LEGACY) != 0 &&
923	    strcmp(mountpoint, ZFS_MOUNTPOINT_NONE) != 0)) {
924		char buf[MAXPATHLEN];
925		DIR *dirp;
926
927		if (mountpoint && mountpoint[0] != '/') {
928			(void) fprintf(stderr, gettext("invalid mountpoint "
929			    "'%s': must be an absolute path, 'legacy', or "
930			    "'none'\n"), mountpoint);
931			goto errout;
932		}
933
934		if (mountpoint == NULL) {
935			if (altroot != NULL)
936				(void) snprintf(buf, sizeof (buf), "%s/%s",
937				    altroot, poolname);
938			else
939				(void) snprintf(buf, sizeof (buf), "/%s",
940				    poolname);
941		} else {
942			if (altroot != NULL)
943				(void) snprintf(buf, sizeof (buf), "%s%s",
944				    altroot, mountpoint);
945			else
946				(void) snprintf(buf, sizeof (buf), "%s",
947				    mountpoint);
948		}
949
950		if ((dirp = opendir(buf)) == NULL && errno != ENOENT) {
951			(void) fprintf(stderr, gettext("mountpoint '%s' : "
952			    "%s\n"), buf, strerror(errno));
953			(void) fprintf(stderr, gettext("use '-m' "
954			    "option to provide a different default\n"));
955			goto errout;
956		} else if (dirp) {
957			int count = 0;
958
959			while (count < 3 && readdir(dirp) != NULL)
960				count++;
961			(void) closedir(dirp);
962
963			if (count > 2) {
964				(void) fprintf(stderr, gettext("mountpoint "
965				    "'%s' exists and is not empty\n"), buf);
966				(void) fprintf(stderr, gettext("use '-m' "
967				    "option to provide a "
968				    "different default\n"));
969				goto errout;
970			}
971		}
972	}
973
974	/*
975	 * Now that the mountpoint's validity has been checked, ensure that
976	 * the property is set appropriately prior to creating the pool.
977	 */
978	if (mountpoint != NULL) {
979		ret = add_prop_list(zfs_prop_to_name(ZFS_PROP_MOUNTPOINT),
980		    mountpoint, &fsprops, B_FALSE);
981		if (ret != 0)
982			goto errout;
983	}
984
985	ret = 1;
986	if (dryrun) {
987		/*
988		 * For a dry run invocation, print out a basic message and run
989		 * through all the vdevs in the list and print out in an
990		 * appropriate hierarchy.
991		 */
992		(void) printf(gettext("would create '%s' with the "
993		    "following layout:\n\n"), poolname);
994
995		print_vdev_tree(NULL, poolname, nvroot, 0, B_FALSE);
996		if (num_logs(nvroot) > 0)
997			print_vdev_tree(NULL, "logs", nvroot, 0, B_TRUE);
998
999		ret = 0;
1000	} else {
1001		/*
1002		 * Hand off to libzfs.
1003		 */
1004		if (enable_all_pool_feat) {
1005			spa_feature_t i;
1006			for (i = 0; i < SPA_FEATURES; i++) {
1007				char propname[MAXPATHLEN];
1008				zfeature_info_t *feat = &spa_feature_table[i];
1009
1010				(void) snprintf(propname, sizeof (propname),
1011				    "feature@%s", feat->fi_uname);
1012
1013				/*
1014				 * Skip feature if user specified it manually
1015				 * on the command line.
1016				 */
1017				if (nvlist_exists(props, propname))
1018					continue;
1019
1020				ret = add_prop_list(propname,
1021				    ZFS_FEATURE_ENABLED, &props, B_TRUE);
1022				if (ret != 0)
1023					goto errout;
1024			}
1025		}
1026
1027		ret = 1;
1028		if (zpool_create(g_zfs, poolname,
1029		    nvroot, props, fsprops) == 0) {
1030			zfs_handle_t *pool = zfs_open(g_zfs, poolname,
1031			    ZFS_TYPE_FILESYSTEM);
1032			if (pool != NULL) {
1033				if (zfs_mount(pool, NULL, 0) == 0)
1034					ret = zfs_shareall(pool);
1035				zfs_close(pool);
1036			}
1037		} else if (libzfs_errno(g_zfs) == EZFS_INVALIDNAME) {
1038			(void) fprintf(stderr, gettext("pool name may have "
1039			    "been omitted\n"));
1040		}
1041	}
1042
1043errout:
1044	nvlist_free(nvroot);
1045	nvlist_free(fsprops);
1046	nvlist_free(props);
1047	return (ret);
1048badusage:
1049	nvlist_free(fsprops);
1050	nvlist_free(props);
1051	usage(B_FALSE);
1052	return (2);
1053}
1054
1055/*
1056 * zpool destroy <pool>
1057 *
1058 * 	-f	Forcefully unmount any datasets
1059 *
1060 * Destroy the given pool.  Automatically unmounts any datasets in the pool.
1061 */
1062int
1063zpool_do_destroy(int argc, char **argv)
1064{
1065	boolean_t force = B_FALSE;
1066	int c;
1067	char *pool;
1068	zpool_handle_t *zhp;
1069	int ret;
1070
1071	/* check options */
1072	while ((c = getopt(argc, argv, "f")) != -1) {
1073		switch (c) {
1074		case 'f':
1075			force = B_TRUE;
1076			break;
1077		case '?':
1078			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
1079			    optopt);
1080			usage(B_FALSE);
1081		}
1082	}
1083
1084	argc -= optind;
1085	argv += optind;
1086
1087	/* check arguments */
1088	if (argc < 1) {
1089		(void) fprintf(stderr, gettext("missing pool argument\n"));
1090		usage(B_FALSE);
1091	}
1092	if (argc > 1) {
1093		(void) fprintf(stderr, gettext("too many arguments\n"));
1094		usage(B_FALSE);
1095	}
1096
1097	pool = argv[0];
1098
1099	if ((zhp = zpool_open_canfail(g_zfs, pool)) == NULL) {
1100		/*
1101		 * As a special case, check for use of '/' in the name, and
1102		 * direct the user to use 'zfs destroy' instead.
1103		 */
1104		if (strchr(pool, '/') != NULL)
1105			(void) fprintf(stderr, gettext("use 'zfs destroy' to "
1106			    "destroy a dataset\n"));
1107		return (1);
1108	}
1109
1110	if (zpool_disable_datasets(zhp, force) != 0) {
1111		(void) fprintf(stderr, gettext("could not destroy '%s': "
1112		    "could not unmount datasets\n"), zpool_get_name(zhp));
1113		return (1);
1114	}
1115
1116	/* The history must be logged as part of the export */
1117	log_history = B_FALSE;
1118
1119	ret = (zpool_destroy(zhp, history_str) != 0);
1120
1121	zpool_close(zhp);
1122
1123	return (ret);
1124}
1125
1126/*
1127 * zpool export [-f] <pool> ...
1128 *
1129 *	-f	Forcefully unmount datasets
1130 *
1131 * Export the given pools.  By default, the command will attempt to cleanly
1132 * unmount any active datasets within the pool.  If the '-f' flag is specified,
1133 * then the datasets will be forcefully unmounted.
1134 */
1135int
1136zpool_do_export(int argc, char **argv)
1137{
1138	boolean_t force = B_FALSE;
1139	boolean_t hardforce = B_FALSE;
1140	int c;
1141	zpool_handle_t *zhp;
1142	int ret;
1143	int i;
1144
1145	/* check options */
1146	while ((c = getopt(argc, argv, "fF")) != -1) {
1147		switch (c) {
1148		case 'f':
1149			force = B_TRUE;
1150			break;
1151		case 'F':
1152			hardforce = B_TRUE;
1153			break;
1154		case '?':
1155			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
1156			    optopt);
1157			usage(B_FALSE);
1158		}
1159	}
1160
1161	argc -= optind;
1162	argv += optind;
1163
1164	/* check arguments */
1165	if (argc < 1) {
1166		(void) fprintf(stderr, gettext("missing pool argument\n"));
1167		usage(B_FALSE);
1168	}
1169
1170	ret = 0;
1171	for (i = 0; i < argc; i++) {
1172		if ((zhp = zpool_open_canfail(g_zfs, argv[i])) == NULL) {
1173			ret = 1;
1174			continue;
1175		}
1176
1177		if (zpool_disable_datasets(zhp, force) != 0) {
1178			ret = 1;
1179			zpool_close(zhp);
1180			continue;
1181		}
1182
1183		/* The history must be logged as part of the export */
1184		log_history = B_FALSE;
1185
1186		if (hardforce) {
1187			if (zpool_export_force(zhp, history_str) != 0)
1188				ret = 1;
1189		} else if (zpool_export(zhp, force, history_str) != 0) {
1190			ret = 1;
1191		}
1192
1193		zpool_close(zhp);
1194	}
1195
1196	return (ret);
1197}
1198
1199/*
1200 * Given a vdev configuration, determine the maximum width needed for the device
1201 * name column.
1202 */
1203static int
1204max_width(zpool_handle_t *zhp, nvlist_t *nv, int depth, int max)
1205{
1206	char *name = zpool_vdev_name(g_zfs, zhp, nv, B_TRUE);
1207	nvlist_t **child;
1208	uint_t c, children;
1209	int ret;
1210
1211	if (strlen(name) + depth > max)
1212		max = strlen(name) + depth;
1213
1214	free(name);
1215
1216	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_SPARES,
1217	    &child, &children) == 0) {
1218		for (c = 0; c < children; c++)
1219			if ((ret = max_width(zhp, child[c], depth + 2,
1220			    max)) > max)
1221				max = ret;
1222	}
1223
1224	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_L2CACHE,
1225	    &child, &children) == 0) {
1226		for (c = 0; c < children; c++)
1227			if ((ret = max_width(zhp, child[c], depth + 2,
1228			    max)) > max)
1229				max = ret;
1230	}
1231
1232	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
1233	    &child, &children) == 0) {
1234		for (c = 0; c < children; c++)
1235			if ((ret = max_width(zhp, child[c], depth + 2,
1236			    max)) > max)
1237				max = ret;
1238	}
1239
1240
1241	return (max);
1242}
1243
1244typedef struct spare_cbdata {
1245	uint64_t	cb_guid;
1246	zpool_handle_t	*cb_zhp;
1247} spare_cbdata_t;
1248
1249static boolean_t
1250find_vdev(nvlist_t *nv, uint64_t search)
1251{
1252	uint64_t guid;
1253	nvlist_t **child;
1254	uint_t c, children;
1255
1256	if (nvlist_lookup_uint64(nv, ZPOOL_CONFIG_GUID, &guid) == 0 &&
1257	    search == guid)
1258		return (B_TRUE);
1259
1260	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
1261	    &child, &children) == 0) {
1262		for (c = 0; c < children; c++)
1263			if (find_vdev(child[c], search))
1264				return (B_TRUE);
1265	}
1266
1267	return (B_FALSE);
1268}
1269
1270static int
1271find_spare(zpool_handle_t *zhp, void *data)
1272{
1273	spare_cbdata_t *cbp = data;
1274	nvlist_t *config, *nvroot;
1275
1276	config = zpool_get_config(zhp, NULL);
1277	verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE,
1278	    &nvroot) == 0);
1279
1280	if (find_vdev(nvroot, cbp->cb_guid)) {
1281		cbp->cb_zhp = zhp;
1282		return (1);
1283	}
1284
1285	zpool_close(zhp);
1286	return (0);
1287}
1288
1289/*
1290 * Print out configuration state as requested by status_callback.
1291 */
1292void
1293print_status_config(zpool_handle_t *zhp, const char *name, nvlist_t *nv,
1294    int namewidth, int depth, boolean_t isspare)
1295{
1296	nvlist_t **child;
1297	uint_t c, vsc, children;
1298	pool_scan_stat_t *ps = NULL;
1299	vdev_stat_t *vs;
1300	char rbuf[6], wbuf[6], cbuf[6];
1301	char *vname;
1302	uint64_t notpresent;
1303	uint64_t ashift;
1304	spare_cbdata_t cb;
1305	const char *state;
1306
1307	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
1308	    &child, &children) != 0)
1309		children = 0;
1310
1311	verify(nvlist_lookup_uint64_array(nv, ZPOOL_CONFIG_VDEV_STATS,
1312	    (uint64_t **)&vs, &vsc) == 0);
1313
1314	state = zpool_state_to_name(vs->vs_state, vs->vs_aux);
1315	if (isspare) {
1316		/*
1317		 * For hot spares, we use the terms 'INUSE' and 'AVAILABLE' for
1318		 * online drives.
1319		 */
1320		if (vs->vs_aux == VDEV_AUX_SPARED)
1321			state = "INUSE";
1322		else if (vs->vs_state == VDEV_STATE_HEALTHY)
1323			state = "AVAIL";
1324	}
1325
1326	(void) printf("\t%*s%-*s  %-8s", depth, "", namewidth - depth,
1327	    name, state);
1328
1329	if (!isspare) {
1330		zfs_nicenum(vs->vs_read_errors, rbuf, sizeof (rbuf));
1331		zfs_nicenum(vs->vs_write_errors, wbuf, sizeof (wbuf));
1332		zfs_nicenum(vs->vs_checksum_errors, cbuf, sizeof (cbuf));
1333		(void) printf(" %5s %5s %5s", rbuf, wbuf, cbuf);
1334	}
1335
1336	if (nvlist_lookup_uint64(nv, ZPOOL_CONFIG_NOT_PRESENT,
1337	    &notpresent) == 0 ||
1338	    vs->vs_state <= VDEV_STATE_CANT_OPEN) {
1339		char *path;
1340		if (nvlist_lookup_string(nv, ZPOOL_CONFIG_PATH, &path) == 0)
1341			(void) printf("  was %s", path);
1342	} else if (vs->vs_aux != 0) {
1343		(void) printf("  ");
1344
1345		switch (vs->vs_aux) {
1346		case VDEV_AUX_OPEN_FAILED:
1347			(void) printf(gettext("cannot open"));
1348			break;
1349
1350		case VDEV_AUX_BAD_GUID_SUM:
1351			(void) printf(gettext("missing device"));
1352			break;
1353
1354		case VDEV_AUX_NO_REPLICAS:
1355			(void) printf(gettext("insufficient replicas"));
1356			break;
1357
1358		case VDEV_AUX_VERSION_NEWER:
1359			(void) printf(gettext("newer version"));
1360			break;
1361
1362		case VDEV_AUX_UNSUP_FEAT:
1363			(void) printf(gettext("unsupported feature(s)"));
1364			break;
1365
1366		case VDEV_AUX_ASHIFT_TOO_BIG:
1367			(void) printf(gettext("unsupported minimum blocksize"));
1368			break;
1369
1370		case VDEV_AUX_SPARED:
1371			verify(nvlist_lookup_uint64(nv, ZPOOL_CONFIG_GUID,
1372			    &cb.cb_guid) == 0);
1373			if (zpool_iter(g_zfs, find_spare, &cb) == 1) {
1374				if (strcmp(zpool_get_name(cb.cb_zhp),
1375				    zpool_get_name(zhp)) == 0)
1376					(void) printf(gettext("currently in "
1377					    "use"));
1378				else
1379					(void) printf(gettext("in use by "
1380					    "pool '%s'"),
1381					    zpool_get_name(cb.cb_zhp));
1382				zpool_close(cb.cb_zhp);
1383			} else {
1384				(void) printf(gettext("currently in use"));
1385			}
1386			break;
1387
1388		case VDEV_AUX_ERR_EXCEEDED:
1389			(void) printf(gettext("too many errors"));
1390			break;
1391
1392		case VDEV_AUX_IO_FAILURE:
1393			(void) printf(gettext("experienced I/O failures"));
1394			break;
1395
1396		case VDEV_AUX_BAD_LOG:
1397			(void) printf(gettext("bad intent log"));
1398			break;
1399
1400		case VDEV_AUX_EXTERNAL:
1401			(void) printf(gettext("external device fault"));
1402			break;
1403
1404		case VDEV_AUX_SPLIT_POOL:
1405			(void) printf(gettext("split into new pool"));
1406			break;
1407
1408		default:
1409			(void) printf(gettext("corrupted data"));
1410			break;
1411		}
1412	} else if (children == 0 && !isspare &&
1413	    VDEV_STAT_VALID(vs_physical_ashift, vsc) &&
1414	    vs->vs_configured_ashift < vs->vs_physical_ashift) {
1415		(void) printf(
1416		    gettext("  block size: %dB configured, %dB native"),
1417		    1 << vs->vs_configured_ashift, 1 << vs->vs_physical_ashift);
1418	}
1419
1420	(void) nvlist_lookup_uint64_array(nv, ZPOOL_CONFIG_SCAN_STATS,
1421	    (uint64_t **)&ps, &c);
1422
1423	if (ps && ps->pss_state == DSS_SCANNING &&
1424	    vs->vs_scan_processed != 0 && children == 0) {
1425		(void) printf(gettext("  (%s)"),
1426		    (ps->pss_func == POOL_SCAN_RESILVER) ?
1427		    "resilvering" : "repairing");
1428	}
1429
1430	(void) printf("\n");
1431
1432	for (c = 0; c < children; c++) {
1433		uint64_t islog = B_FALSE, ishole = B_FALSE;
1434
1435		/* Don't print logs or holes here */
1436		(void) nvlist_lookup_uint64(child[c], ZPOOL_CONFIG_IS_LOG,
1437		    &islog);
1438		(void) nvlist_lookup_uint64(child[c], ZPOOL_CONFIG_IS_HOLE,
1439		    &ishole);
1440		if (islog || ishole)
1441			continue;
1442		vname = zpool_vdev_name(g_zfs, zhp, child[c], B_TRUE);
1443		print_status_config(zhp, vname, child[c],
1444		    namewidth, depth + 2, isspare);
1445		free(vname);
1446	}
1447}
1448
1449
1450/*
1451 * Print the configuration of an exported pool.  Iterate over all vdevs in the
1452 * pool, printing out the name and status for each one.
1453 */
1454void
1455print_import_config(const char *name, nvlist_t *nv, int namewidth, int depth)
1456{
1457	nvlist_t **child;
1458	uint_t c, children;
1459	vdev_stat_t *vs;
1460	char *type, *vname;
1461
1462	verify(nvlist_lookup_string(nv, ZPOOL_CONFIG_TYPE, &type) == 0);
1463	if (strcmp(type, VDEV_TYPE_MISSING) == 0 ||
1464	    strcmp(type, VDEV_TYPE_HOLE) == 0)
1465		return;
1466
1467	verify(nvlist_lookup_uint64_array(nv, ZPOOL_CONFIG_VDEV_STATS,
1468	    (uint64_t **)&vs, &c) == 0);
1469
1470	(void) printf("\t%*s%-*s", depth, "", namewidth - depth, name);
1471	(void) printf("  %s", zpool_state_to_name(vs->vs_state, vs->vs_aux));
1472
1473	if (vs->vs_aux != 0) {
1474		(void) printf("  ");
1475
1476		switch (vs->vs_aux) {
1477		case VDEV_AUX_OPEN_FAILED:
1478			(void) printf(gettext("cannot open"));
1479			break;
1480
1481		case VDEV_AUX_BAD_GUID_SUM:
1482			(void) printf(gettext("missing device"));
1483			break;
1484
1485		case VDEV_AUX_NO_REPLICAS:
1486			(void) printf(gettext("insufficient replicas"));
1487			break;
1488
1489		case VDEV_AUX_VERSION_NEWER:
1490			(void) printf(gettext("newer version"));
1491			break;
1492
1493		case VDEV_AUX_UNSUP_FEAT:
1494			(void) printf(gettext("unsupported feature(s)"));
1495			break;
1496
1497		case VDEV_AUX_ERR_EXCEEDED:
1498			(void) printf(gettext("too many errors"));
1499			break;
1500
1501		default:
1502			(void) printf(gettext("corrupted data"));
1503			break;
1504		}
1505	}
1506	(void) printf("\n");
1507
1508	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
1509	    &child, &children) != 0)
1510		return;
1511
1512	for (c = 0; c < children; c++) {
1513		uint64_t is_log = B_FALSE;
1514
1515		(void) nvlist_lookup_uint64(child[c], ZPOOL_CONFIG_IS_LOG,
1516		    &is_log);
1517		if (is_log)
1518			continue;
1519
1520		vname = zpool_vdev_name(g_zfs, NULL, child[c], B_TRUE);
1521		print_import_config(vname, child[c], namewidth, depth + 2);
1522		free(vname);
1523	}
1524
1525	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_L2CACHE,
1526	    &child, &children) == 0) {
1527		(void) printf(gettext("\tcache\n"));
1528		for (c = 0; c < children; c++) {
1529			vname = zpool_vdev_name(g_zfs, NULL, child[c], B_FALSE);
1530			(void) printf("\t  %s\n", vname);
1531			free(vname);
1532		}
1533	}
1534
1535	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_SPARES,
1536	    &child, &children) == 0) {
1537		(void) printf(gettext("\tspares\n"));
1538		for (c = 0; c < children; c++) {
1539			vname = zpool_vdev_name(g_zfs, NULL, child[c], B_FALSE);
1540			(void) printf("\t  %s\n", vname);
1541			free(vname);
1542		}
1543	}
1544}
1545
1546/*
1547 * Print log vdevs.
1548 * Logs are recorded as top level vdevs in the main pool child array
1549 * but with "is_log" set to 1. We use either print_status_config() or
1550 * print_import_config() to print the top level logs then any log
1551 * children (eg mirrored slogs) are printed recursively - which
1552 * works because only the top level vdev is marked "is_log"
1553 */
1554static void
1555print_logs(zpool_handle_t *zhp, nvlist_t *nv, int namewidth, boolean_t verbose)
1556{
1557	uint_t c, children;
1558	nvlist_t **child;
1559
1560	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN, &child,
1561	    &children) != 0)
1562		return;
1563
1564	(void) printf(gettext("\tlogs\n"));
1565
1566	for (c = 0; c < children; c++) {
1567		uint64_t is_log = B_FALSE;
1568		char *name;
1569
1570		(void) nvlist_lookup_uint64(child[c], ZPOOL_CONFIG_IS_LOG,
1571		    &is_log);
1572		if (!is_log)
1573			continue;
1574		name = zpool_vdev_name(g_zfs, zhp, child[c], B_TRUE);
1575		if (verbose)
1576			print_status_config(zhp, name, child[c], namewidth,
1577			    2, B_FALSE);
1578		else
1579			print_import_config(name, child[c], namewidth, 2);
1580		free(name);
1581	}
1582}
1583
1584/*
1585 * Display the status for the given pool.
1586 */
1587static void
1588show_import(nvlist_t *config)
1589{
1590	uint64_t pool_state;
1591	vdev_stat_t *vs;
1592	char *name;
1593	uint64_t guid;
1594	char *msgid;
1595	nvlist_t *nvroot;
1596	int reason;
1597	const char *health;
1598	uint_t vsc;
1599	int namewidth;
1600	char *comment;
1601
1602	verify(nvlist_lookup_string(config, ZPOOL_CONFIG_POOL_NAME,
1603	    &name) == 0);
1604	verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_GUID,
1605	    &guid) == 0);
1606	verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_STATE,
1607	    &pool_state) == 0);
1608	verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE,
1609	    &nvroot) == 0);
1610
1611	verify(nvlist_lookup_uint64_array(nvroot, ZPOOL_CONFIG_VDEV_STATS,
1612	    (uint64_t **)&vs, &vsc) == 0);
1613	health = zpool_state_to_name(vs->vs_state, vs->vs_aux);
1614
1615	reason = zpool_import_status(config, &msgid);
1616
1617	(void) printf(gettext("   pool: %s\n"), name);
1618	(void) printf(gettext("     id: %llu\n"), (u_longlong_t)guid);
1619	(void) printf(gettext("  state: %s"), health);
1620	if (pool_state == POOL_STATE_DESTROYED)
1621		(void) printf(gettext(" (DESTROYED)"));
1622	(void) printf("\n");
1623
1624	switch (reason) {
1625	case ZPOOL_STATUS_MISSING_DEV_R:
1626	case ZPOOL_STATUS_MISSING_DEV_NR:
1627	case ZPOOL_STATUS_BAD_GUID_SUM:
1628		(void) printf(gettext(" status: One or more devices are "
1629		    "missing from the system.\n"));
1630		break;
1631
1632	case ZPOOL_STATUS_CORRUPT_LABEL_R:
1633	case ZPOOL_STATUS_CORRUPT_LABEL_NR:
1634		(void) printf(gettext(" status: One or more devices contains "
1635		    "corrupted data.\n"));
1636		break;
1637
1638	case ZPOOL_STATUS_CORRUPT_DATA:
1639		(void) printf(
1640		    gettext(" status: The pool data is corrupted.\n"));
1641		break;
1642
1643	case ZPOOL_STATUS_OFFLINE_DEV:
1644		(void) printf(gettext(" status: One or more devices "
1645		    "are offlined.\n"));
1646		break;
1647
1648	case ZPOOL_STATUS_CORRUPT_POOL:
1649		(void) printf(gettext(" status: The pool metadata is "
1650		    "corrupted.\n"));
1651		break;
1652
1653	case ZPOOL_STATUS_VERSION_OLDER:
1654		(void) printf(gettext(" status: The pool is formatted using a "
1655		    "legacy on-disk version.\n"));
1656		break;
1657
1658	case ZPOOL_STATUS_VERSION_NEWER:
1659		(void) printf(gettext(" status: The pool is formatted using an "
1660		    "incompatible version.\n"));
1661		break;
1662
1663	case ZPOOL_STATUS_FEAT_DISABLED:
1664		(void) printf(gettext(" status: Some supported features are "
1665		    "not enabled on the pool.\n"));
1666		break;
1667
1668	case ZPOOL_STATUS_UNSUP_FEAT_READ:
1669		(void) printf(gettext("status: The pool uses the following "
1670		    "feature(s) not supported on this sytem:\n"));
1671		zpool_print_unsup_feat(config);
1672		break;
1673
1674	case ZPOOL_STATUS_UNSUP_FEAT_WRITE:
1675		(void) printf(gettext("status: The pool can only be accessed "
1676		    "in read-only mode on this system. It\n\tcannot be "
1677		    "accessed in read-write mode because it uses the "
1678		    "following\n\tfeature(s) not supported on this system:\n"));
1679		zpool_print_unsup_feat(config);
1680		break;
1681
1682	case ZPOOL_STATUS_HOSTID_MISMATCH:
1683		(void) printf(gettext(" status: The pool was last accessed by "
1684		    "another system.\n"));
1685		break;
1686
1687	case ZPOOL_STATUS_FAULTED_DEV_R:
1688	case ZPOOL_STATUS_FAULTED_DEV_NR:
1689		(void) printf(gettext(" status: One or more devices are "
1690		    "faulted.\n"));
1691		break;
1692
1693	case ZPOOL_STATUS_BAD_LOG:
1694		(void) printf(gettext(" status: An intent log record cannot be "
1695		    "read.\n"));
1696		break;
1697
1698	case ZPOOL_STATUS_RESILVERING:
1699		(void) printf(gettext(" status: One or more devices were being "
1700		    "resilvered.\n"));
1701		break;
1702
1703	default:
1704		/*
1705		 * No other status can be seen when importing pools.
1706		 */
1707		assert(reason == ZPOOL_STATUS_OK);
1708	}
1709
1710	/*
1711	 * Print out an action according to the overall state of the pool.
1712	 */
1713	if (vs->vs_state == VDEV_STATE_HEALTHY) {
1714		if (reason == ZPOOL_STATUS_VERSION_OLDER ||
1715		    reason == ZPOOL_STATUS_FEAT_DISABLED) {
1716			(void) printf(gettext(" action: The pool can be "
1717			    "imported using its name or numeric identifier, "
1718			    "though\n\tsome features will not be available "
1719			    "without an explicit 'zpool upgrade'.\n"));
1720		} else if (reason == ZPOOL_STATUS_HOSTID_MISMATCH) {
1721			(void) printf(gettext(" action: The pool can be "
1722			    "imported using its name or numeric "
1723			    "identifier and\n\tthe '-f' flag.\n"));
1724		} else {
1725			(void) printf(gettext(" action: The pool can be "
1726			    "imported using its name or numeric "
1727			    "identifier.\n"));
1728		}
1729	} else if (vs->vs_state == VDEV_STATE_DEGRADED) {
1730		(void) printf(gettext(" action: The pool can be imported "
1731		    "despite missing or damaged devices.  The\n\tfault "
1732		    "tolerance of the pool may be compromised if imported.\n"));
1733	} else {
1734		switch (reason) {
1735		case ZPOOL_STATUS_VERSION_NEWER:
1736			(void) printf(gettext(" action: The pool cannot be "
1737			    "imported.  Access the pool on a system running "
1738			    "newer\n\tsoftware, or recreate the pool from "
1739			    "backup.\n"));
1740			break;
1741		case ZPOOL_STATUS_UNSUP_FEAT_READ:
1742			(void) printf(gettext("action: The pool cannot be "
1743			    "imported. Access the pool on a system that "
1744			    "supports\n\tthe required feature(s), or recreate "
1745			    "the pool from backup.\n"));
1746			break;
1747		case ZPOOL_STATUS_UNSUP_FEAT_WRITE:
1748			(void) printf(gettext("action: The pool cannot be "
1749			    "imported in read-write mode. Import the pool "
1750			    "with\n"
1751			    "\t\"-o readonly=on\", access the pool on a system "
1752			    "that supports the\n\trequired feature(s), or "
1753			    "recreate the pool from backup.\n"));
1754			break;
1755		case ZPOOL_STATUS_MISSING_DEV_R:
1756		case ZPOOL_STATUS_MISSING_DEV_NR:
1757		case ZPOOL_STATUS_BAD_GUID_SUM:
1758			(void) printf(gettext(" action: The pool cannot be "
1759			    "imported. Attach the missing\n\tdevices and try "
1760			    "again.\n"));
1761			break;
1762		default:
1763			(void) printf(gettext(" action: The pool cannot be "
1764			    "imported due to damaged devices or data.\n"));
1765		}
1766	}
1767
1768	/* Print the comment attached to the pool. */
1769	if (nvlist_lookup_string(config, ZPOOL_CONFIG_COMMENT, &comment) == 0)
1770		(void) printf(gettext("comment: %s\n"), comment);
1771
1772	/*
1773	 * If the state is "closed" or "can't open", and the aux state
1774	 * is "corrupt data":
1775	 */
1776	if (((vs->vs_state == VDEV_STATE_CLOSED) ||
1777	    (vs->vs_state == VDEV_STATE_CANT_OPEN)) &&
1778	    (vs->vs_aux == VDEV_AUX_CORRUPT_DATA)) {
1779		if (pool_state == POOL_STATE_DESTROYED)
1780			(void) printf(gettext("\tThe pool was destroyed, "
1781			    "but can be imported using the '-Df' flags.\n"));
1782		else if (pool_state != POOL_STATE_EXPORTED)
1783			(void) printf(gettext("\tThe pool may be active on "
1784			    "another system, but can be imported using\n\t"
1785			    "the '-f' flag.\n"));
1786	}
1787
1788	if (msgid != NULL)
1789		(void) printf(gettext("   see: http://illumos.org/msg/%s\n"),
1790		    msgid);
1791
1792	(void) printf(gettext(" config:\n\n"));
1793
1794	namewidth = max_width(NULL, nvroot, 0, 0);
1795	if (namewidth < 10)
1796		namewidth = 10;
1797
1798	print_import_config(name, nvroot, namewidth, 0);
1799	if (num_logs(nvroot) > 0)
1800		print_logs(NULL, nvroot, namewidth, B_FALSE);
1801
1802	if (reason == ZPOOL_STATUS_BAD_GUID_SUM) {
1803		(void) printf(gettext("\n\tAdditional devices are known to "
1804		    "be part of this pool, though their\n\texact "
1805		    "configuration cannot be determined.\n"));
1806	}
1807}
1808
1809/*
1810 * Perform the import for the given configuration.  This passes the heavy
1811 * lifting off to zpool_import_props(), and then mounts the datasets contained
1812 * within the pool.
1813 */
1814static int
1815do_import(nvlist_t *config, const char *newname, const char *mntopts,
1816    nvlist_t *props, int flags)
1817{
1818	zpool_handle_t *zhp;
1819	char *name;
1820	uint64_t state;
1821	uint64_t version;
1822
1823	verify(nvlist_lookup_string(config, ZPOOL_CONFIG_POOL_NAME,
1824	    &name) == 0);
1825
1826	verify(nvlist_lookup_uint64(config,
1827	    ZPOOL_CONFIG_POOL_STATE, &state) == 0);
1828	verify(nvlist_lookup_uint64(config,
1829	    ZPOOL_CONFIG_VERSION, &version) == 0);
1830	if (!SPA_VERSION_IS_SUPPORTED(version)) {
1831		(void) fprintf(stderr, gettext("cannot import '%s': pool "
1832		    "is formatted using an unsupported ZFS version\n"), name);
1833		return (1);
1834	} else if (state != POOL_STATE_EXPORTED &&
1835	    !(flags & ZFS_IMPORT_ANY_HOST)) {
1836		uint64_t hostid;
1837
1838		if (nvlist_lookup_uint64(config, ZPOOL_CONFIG_HOSTID,
1839		    &hostid) == 0) {
1840			if ((unsigned long)hostid != gethostid()) {
1841				char *hostname;
1842				uint64_t timestamp;
1843				time_t t;
1844
1845				verify(nvlist_lookup_string(config,
1846				    ZPOOL_CONFIG_HOSTNAME, &hostname) == 0);
1847				verify(nvlist_lookup_uint64(config,
1848				    ZPOOL_CONFIG_TIMESTAMP, &timestamp) == 0);
1849				t = timestamp;
1850				(void) fprintf(stderr, gettext("cannot import "
1851				    "'%s': pool may be in use from other "
1852				    "system, it was last accessed by %s "
1853				    "(hostid: 0x%lx) on %s"), name, hostname,
1854				    (unsigned long)hostid,
1855				    asctime(localtime(&t)));
1856				(void) fprintf(stderr, gettext("use '-f' to "
1857				    "import anyway\n"));
1858				return (1);
1859			}
1860		} else {
1861			(void) fprintf(stderr, gettext("cannot import '%s': "
1862			    "pool may be in use from other system\n"), name);
1863			(void) fprintf(stderr, gettext("use '-f' to import "
1864			    "anyway\n"));
1865			return (1);
1866		}
1867	}
1868
1869	if (zpool_import_props(g_zfs, config, newname, props, flags) != 0)
1870		return (1);
1871
1872	if (newname != NULL)
1873		name = (char *)newname;
1874
1875	if ((zhp = zpool_open_canfail(g_zfs, name)) == NULL)
1876		return (1);
1877
1878	if (zpool_get_state(zhp) != POOL_STATE_UNAVAIL &&
1879	    !(flags & ZFS_IMPORT_ONLY) &&
1880	    zpool_enable_datasets(zhp, mntopts, 0) != 0) {
1881		zpool_close(zhp);
1882		return (1);
1883	}
1884
1885	zpool_close(zhp);
1886	return (0);
1887}
1888
1889/*
1890 * zpool import [-d dir] [-D]
1891 *       import [-o mntopts] [-o prop=value] ... [-R root] [-D]
1892 *              [-d dir | -c cachefile] [-f] -a
1893 *       import [-o mntopts] [-o prop=value] ... [-R root] [-D]
1894 *              [-d dir | -c cachefile] [-f] [-n] [-F] <pool | id> [newpool]
1895 *
1896 *	 -c	Read pool information from a cachefile instead of searching
1897 *		devices.
1898 *
1899 *       -d	Scan in a specific directory, other than /dev/dsk.  More than
1900 *		one directory can be specified using multiple '-d' options.
1901 *
1902 *       -D     Scan for previously destroyed pools or import all or only
1903 *              specified destroyed pools.
1904 *
1905 *       -R	Temporarily import the pool, with all mountpoints relative to
1906 *		the given root.  The pool will remain exported when the machine
1907 *		is rebooted.
1908 *
1909 *       -V	Import even in the presence of faulted vdevs.  This is an
1910 *       	intentionally undocumented option for testing purposes, and
1911 *       	treats the pool configuration as complete, leaving any bad
1912 *		vdevs in the FAULTED state. In other words, it does verbatim
1913 *		import.
1914 *
1915 *       -f	Force import, even if it appears that the pool is active.
1916 *
1917 *       -F     Attempt rewind if necessary.
1918 *
1919 *       -n     See if rewind would work, but don't actually rewind.
1920 *
1921 *       -N     Import the pool but don't mount datasets.
1922 *
1923 *       -T     Specify a starting txg to use for import. This option is
1924 *       	intentionally undocumented option for testing purposes.
1925 *
1926 *       -a	Import all pools found.
1927 *
1928 *       -o	Set property=value and/or temporary mount options (without '=').
1929 *
1930 * The import command scans for pools to import, and import pools based on pool
1931 * name and GUID.  The pool can also be renamed as part of the import process.
1932 */
1933int
1934zpool_do_import(int argc, char **argv)
1935{
1936	char **searchdirs = NULL;
1937	int nsearch = 0;
1938	int c;
1939	int err = 0;
1940	nvlist_t *pools = NULL;
1941	boolean_t do_all = B_FALSE;
1942	boolean_t do_destroyed = B_FALSE;
1943	char *mntopts = NULL;
1944	nvpair_t *elem;
1945	nvlist_t *config;
1946	uint64_t searchguid = 0;
1947	char *searchname = NULL;
1948	char *propval;
1949	nvlist_t *found_config;
1950	nvlist_t *policy = NULL;
1951	nvlist_t *props = NULL;
1952	boolean_t first;
1953	int flags = ZFS_IMPORT_NORMAL;
1954	uint32_t rewind_policy = ZPOOL_NO_REWIND;
1955	boolean_t dryrun = B_FALSE;
1956	boolean_t do_rewind = B_FALSE;
1957	boolean_t xtreme_rewind = B_FALSE;
1958	uint64_t pool_state, txg = -1ULL;
1959	char *cachefile = NULL;
1960	importargs_t idata = { 0 };
1961	char *endptr;
1962
1963	/* check options */
1964	while ((c = getopt(argc, argv, ":aCc:d:DEfFmnNo:R:T:VX")) != -1) {
1965		switch (c) {
1966		case 'a':
1967			do_all = B_TRUE;
1968			break;
1969		case 'c':
1970			cachefile = optarg;
1971			break;
1972		case 'd':
1973			if (searchdirs == NULL) {
1974				searchdirs = safe_malloc(sizeof (char *));
1975			} else {
1976				char **tmp = safe_malloc((nsearch + 1) *
1977				    sizeof (char *));
1978				bcopy(searchdirs, tmp, nsearch *
1979				    sizeof (char *));
1980				free(searchdirs);
1981				searchdirs = tmp;
1982			}
1983			searchdirs[nsearch++] = optarg;
1984			break;
1985		case 'D':
1986			do_destroyed = B_TRUE;
1987			break;
1988		case 'f':
1989			flags |= ZFS_IMPORT_ANY_HOST;
1990			break;
1991		case 'F':
1992			do_rewind = B_TRUE;
1993			break;
1994		case 'm':
1995			flags |= ZFS_IMPORT_MISSING_LOG;
1996			break;
1997		case 'n':
1998			dryrun = B_TRUE;
1999			break;
2000		case 'N':
2001			flags |= ZFS_IMPORT_ONLY;
2002			break;
2003		case 'o':
2004			if ((propval = strchr(optarg, '=')) != NULL) {
2005				*propval = '\0';
2006				propval++;
2007				if (add_prop_list(optarg, propval,
2008				    &props, B_TRUE))
2009					goto error;
2010			} else {
2011				mntopts = optarg;
2012			}
2013			break;
2014		case 'R':
2015			if (add_prop_list(zpool_prop_to_name(
2016			    ZPOOL_PROP_ALTROOT), optarg, &props, B_TRUE))
2017				goto error;
2018			if (nvlist_lookup_string(props,
2019			    zpool_prop_to_name(ZPOOL_PROP_CACHEFILE),
2020			    &propval) == 0)
2021				break;
2022			if (add_prop_list(zpool_prop_to_name(
2023			    ZPOOL_PROP_CACHEFILE), "none", &props, B_TRUE))
2024				goto error;
2025			break;
2026		case 'T':
2027			errno = 0;
2028			txg = strtoull(optarg, &endptr, 10);
2029			if (errno != 0 || *endptr != '\0') {
2030				(void) fprintf(stderr,
2031				    gettext("invalid txg value\n"));
2032				usage(B_FALSE);
2033			}
2034			rewind_policy = ZPOOL_DO_REWIND | ZPOOL_EXTREME_REWIND;
2035			break;
2036		case 'V':
2037			flags |= ZFS_IMPORT_VERBATIM;
2038			break;
2039		case 'X':
2040			xtreme_rewind = B_TRUE;
2041			break;
2042		case ':':
2043			(void) fprintf(stderr, gettext("missing argument for "
2044			    "'%c' option\n"), optopt);
2045			usage(B_FALSE);
2046			break;
2047		case '?':
2048			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
2049			    optopt);
2050			usage(B_FALSE);
2051		}
2052	}
2053
2054	argc -= optind;
2055	argv += optind;
2056
2057	if (cachefile && nsearch != 0) {
2058		(void) fprintf(stderr, gettext("-c is incompatible with -d\n"));
2059		usage(B_FALSE);
2060	}
2061
2062	if ((dryrun || xtreme_rewind) && !do_rewind) {
2063		(void) fprintf(stderr,
2064		    gettext("-n or -X only meaningful with -F\n"));
2065		usage(B_FALSE);
2066	}
2067	if (dryrun)
2068		rewind_policy = ZPOOL_TRY_REWIND;
2069	else if (do_rewind)
2070		rewind_policy = ZPOOL_DO_REWIND;
2071	if (xtreme_rewind)
2072		rewind_policy |= ZPOOL_EXTREME_REWIND;
2073
2074	/* In the future, we can capture further policy and include it here */
2075	if (nvlist_alloc(&policy, NV_UNIQUE_NAME, 0) != 0 ||
2076	    nvlist_add_uint64(policy, ZPOOL_REWIND_REQUEST_TXG, txg) != 0 ||
2077	    nvlist_add_uint32(policy, ZPOOL_REWIND_REQUEST, rewind_policy) != 0)
2078		goto error;
2079
2080	if (searchdirs == NULL) {
2081		searchdirs = safe_malloc(sizeof (char *));
2082		searchdirs[0] = "/dev";
2083		nsearch = 1;
2084	}
2085
2086	/* check argument count */
2087	if (do_all) {
2088		if (argc != 0) {
2089			(void) fprintf(stderr, gettext("too many arguments\n"));
2090			usage(B_FALSE);
2091		}
2092	} else {
2093		if (argc > 2) {
2094			(void) fprintf(stderr, gettext("too many arguments\n"));
2095			usage(B_FALSE);
2096		}
2097
2098		/*
2099		 * Check for the SYS_CONFIG privilege.  We do this explicitly
2100		 * here because otherwise any attempt to discover pools will
2101		 * silently fail.
2102		 */
2103		if (argc == 0 && !priv_ineffect(PRIV_SYS_CONFIG)) {
2104			(void) fprintf(stderr, gettext("cannot "
2105			    "discover pools: permission denied\n"));
2106			free(searchdirs);
2107			nvlist_free(policy);
2108			return (1);
2109		}
2110	}
2111
2112	/*
2113	 * Depending on the arguments given, we do one of the following:
2114	 *
2115	 *	<none>	Iterate through all pools and display information about
2116	 *		each one.
2117	 *
2118	 *	-a	Iterate through all pools and try to import each one.
2119	 *
2120	 *	<id>	Find the pool that corresponds to the given GUID/pool
2121	 *		name and import that one.
2122	 *
2123	 *	-D	Above options applies only to destroyed pools.
2124	 */
2125	if (argc != 0) {
2126		char *endptr;
2127
2128		errno = 0;
2129		searchguid = strtoull(argv[0], &endptr, 10);
2130		if (errno != 0 || *endptr != '\0')
2131			searchname = argv[0];
2132		found_config = NULL;
2133
2134		/*
2135		 * User specified a name or guid.  Ensure it's unique.
2136		 */
2137		idata.unique = B_TRUE;
2138	}
2139
2140
2141	idata.path = searchdirs;
2142	idata.paths = nsearch;
2143	idata.poolname = searchname;
2144	idata.guid = searchguid;
2145	idata.cachefile = cachefile;
2146
2147	pools = zpool_search_import(g_zfs, &idata);
2148
2149	if (pools != NULL && idata.exists &&
2150	    (argc == 1 || strcmp(argv[0], argv[1]) == 0)) {
2151		(void) fprintf(stderr, gettext("cannot import '%s': "
2152		    "a pool with that name already exists\n"),
2153		    argv[0]);
2154		(void) fprintf(stderr, gettext("use the form '%s "
2155		    "<pool | id> <newpool>' to give it a new name\n"),
2156		    "zpool import");
2157		err = 1;
2158	} else if (pools == NULL && idata.exists) {
2159		(void) fprintf(stderr, gettext("cannot import '%s': "
2160		    "a pool with that name is already created/imported,\n"),
2161		    argv[0]);
2162		(void) fprintf(stderr, gettext("and no additional pools "
2163		    "with that name were found\n"));
2164		err = 1;
2165	} else if (pools == NULL) {
2166		if (argc != 0) {
2167			(void) fprintf(stderr, gettext("cannot import '%s': "
2168			    "no such pool available\n"), argv[0]);
2169		}
2170		err = 1;
2171	}
2172
2173	if (err == 1) {
2174		free(searchdirs);
2175		nvlist_free(policy);
2176		return (1);
2177	}
2178
2179	/*
2180	 * At this point we have a list of import candidate configs. Even if
2181	 * we were searching by pool name or guid, we still need to
2182	 * post-process the list to deal with pool state and possible
2183	 * duplicate names.
2184	 */
2185	err = 0;
2186	elem = NULL;
2187	first = B_TRUE;
2188	while ((elem = nvlist_next_nvpair(pools, elem)) != NULL) {
2189
2190		verify(nvpair_value_nvlist(elem, &config) == 0);
2191
2192		verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_STATE,
2193		    &pool_state) == 0);
2194		if (!do_destroyed && pool_state == POOL_STATE_DESTROYED)
2195			continue;
2196		if (do_destroyed && pool_state != POOL_STATE_DESTROYED)
2197			continue;
2198
2199		verify(nvlist_add_nvlist(config, ZPOOL_REWIND_POLICY,
2200		    policy) == 0);
2201
2202		if (argc == 0) {
2203			if (first)
2204				first = B_FALSE;
2205			else if (!do_all)
2206				(void) printf("\n");
2207
2208			if (do_all) {
2209				err |= do_import(config, NULL, mntopts,
2210				    props, flags);
2211			} else {
2212				show_import(config);
2213			}
2214		} else if (searchname != NULL) {
2215			char *name;
2216
2217			/*
2218			 * We are searching for a pool based on name.
2219			 */
2220			verify(nvlist_lookup_string(config,
2221			    ZPOOL_CONFIG_POOL_NAME, &name) == 0);
2222
2223			if (strcmp(name, searchname) == 0) {
2224				if (found_config != NULL) {
2225					(void) fprintf(stderr, gettext(
2226					    "cannot import '%s': more than "
2227					    "one matching pool\n"), searchname);
2228					(void) fprintf(stderr, gettext(
2229					    "import by numeric ID instead\n"));
2230					err = B_TRUE;
2231				}
2232				found_config = config;
2233			}
2234		} else {
2235			uint64_t guid;
2236
2237			/*
2238			 * Search for a pool by guid.
2239			 */
2240			verify(nvlist_lookup_uint64(config,
2241			    ZPOOL_CONFIG_POOL_GUID, &guid) == 0);
2242
2243			if (guid == searchguid)
2244				found_config = config;
2245		}
2246	}
2247
2248	/*
2249	 * If we were searching for a specific pool, verify that we found a
2250	 * pool, and then do the import.
2251	 */
2252	if (argc != 0 && err == 0) {
2253		if (found_config == NULL) {
2254			(void) fprintf(stderr, gettext("cannot import '%s': "
2255			    "no such pool available\n"), argv[0]);
2256			err = B_TRUE;
2257		} else {
2258			err |= do_import(found_config, argc == 1 ? NULL :
2259			    argv[1], mntopts, props, flags);
2260		}
2261	}
2262
2263	/*
2264	 * If we were just looking for pools, report an error if none were
2265	 * found.
2266	 */
2267	if (argc == 0 && first)
2268		(void) fprintf(stderr,
2269		    gettext("no pools available to import\n"));
2270
2271error:
2272	nvlist_free(props);
2273	nvlist_free(pools);
2274	nvlist_free(policy);
2275	free(searchdirs);
2276
2277	return (err ? 1 : 0);
2278}
2279
2280typedef struct iostat_cbdata {
2281	boolean_t cb_verbose;
2282	int cb_namewidth;
2283	int cb_iteration;
2284	zpool_list_t *cb_list;
2285} iostat_cbdata_t;
2286
2287static void
2288print_iostat_separator(iostat_cbdata_t *cb)
2289{
2290	int i = 0;
2291
2292	for (i = 0; i < cb->cb_namewidth; i++)
2293		(void) printf("-");
2294	(void) printf("  -----  -----  -----  -----  -----  -----\n");
2295}
2296
2297static void
2298print_iostat_header(iostat_cbdata_t *cb)
2299{
2300	(void) printf("%*s     capacity     operations    bandwidth\n",
2301	    cb->cb_namewidth, "");
2302	(void) printf("%-*s  alloc   free   read  write   read  write\n",
2303	    cb->cb_namewidth, "pool");
2304	print_iostat_separator(cb);
2305}
2306
2307/*
2308 * Display a single statistic.
2309 */
2310static void
2311print_one_stat(uint64_t value)
2312{
2313	char buf[64];
2314
2315	zfs_nicenum(value, buf, sizeof (buf));
2316	(void) printf("  %5s", buf);
2317}
2318
2319/*
2320 * Print out all the statistics for the given vdev.  This can either be the
2321 * toplevel configuration, or called recursively.  If 'name' is NULL, then this
2322 * is a verbose output, and we don't want to display the toplevel pool stats.
2323 */
2324void
2325print_vdev_stats(zpool_handle_t *zhp, const char *name, nvlist_t *oldnv,
2326    nvlist_t *newnv, iostat_cbdata_t *cb, int depth)
2327{
2328	nvlist_t **oldchild, **newchild;
2329	uint_t c, children;
2330	vdev_stat_t *oldvs, *newvs;
2331	vdev_stat_t zerovs = { 0 };
2332	uint64_t tdelta;
2333	double scale;
2334	char *vname;
2335
2336	if (oldnv != NULL) {
2337		verify(nvlist_lookup_uint64_array(oldnv,
2338		    ZPOOL_CONFIG_VDEV_STATS, (uint64_t **)&oldvs, &c) == 0);
2339	} else {
2340		oldvs = &zerovs;
2341	}
2342
2343	verify(nvlist_lookup_uint64_array(newnv, ZPOOL_CONFIG_VDEV_STATS,
2344	    (uint64_t **)&newvs, &c) == 0);
2345
2346	if (strlen(name) + depth > cb->cb_namewidth)
2347		(void) printf("%*s%s", depth, "", name);
2348	else
2349		(void) printf("%*s%s%*s", depth, "", name,
2350		    (int)(cb->cb_namewidth - strlen(name) - depth), "");
2351
2352	tdelta = newvs->vs_timestamp - oldvs->vs_timestamp;
2353
2354	if (tdelta == 0)
2355		scale = 1.0;
2356	else
2357		scale = (double)NANOSEC / tdelta;
2358
2359	/* only toplevel vdevs have capacity stats */
2360	if (newvs->vs_space == 0) {
2361		(void) printf("      -      -");
2362	} else {
2363		print_one_stat(newvs->vs_alloc);
2364		print_one_stat(newvs->vs_space - newvs->vs_alloc);
2365	}
2366
2367	print_one_stat((uint64_t)(scale * (newvs->vs_ops[ZIO_TYPE_READ] -
2368	    oldvs->vs_ops[ZIO_TYPE_READ])));
2369
2370	print_one_stat((uint64_t)(scale * (newvs->vs_ops[ZIO_TYPE_WRITE] -
2371	    oldvs->vs_ops[ZIO_TYPE_WRITE])));
2372
2373	print_one_stat((uint64_t)(scale * (newvs->vs_bytes[ZIO_TYPE_READ] -
2374	    oldvs->vs_bytes[ZIO_TYPE_READ])));
2375
2376	print_one_stat((uint64_t)(scale * (newvs->vs_bytes[ZIO_TYPE_WRITE] -
2377	    oldvs->vs_bytes[ZIO_TYPE_WRITE])));
2378
2379	(void) printf("\n");
2380
2381	if (!cb->cb_verbose)
2382		return;
2383
2384	if (nvlist_lookup_nvlist_array(newnv, ZPOOL_CONFIG_CHILDREN,
2385	    &newchild, &children) != 0)
2386		return;
2387
2388	if (oldnv && nvlist_lookup_nvlist_array(oldnv, ZPOOL_CONFIG_CHILDREN,
2389	    &oldchild, &c) != 0)
2390		return;
2391
2392	for (c = 0; c < children; c++) {
2393		uint64_t ishole = B_FALSE, islog = B_FALSE;
2394
2395		(void) nvlist_lookup_uint64(newchild[c], ZPOOL_CONFIG_IS_HOLE,
2396		    &ishole);
2397
2398		(void) nvlist_lookup_uint64(newchild[c], ZPOOL_CONFIG_IS_LOG,
2399		    &islog);
2400
2401		if (ishole || islog)
2402			continue;
2403
2404		vname = zpool_vdev_name(g_zfs, zhp, newchild[c], B_FALSE);
2405		print_vdev_stats(zhp, vname, oldnv ? oldchild[c] : NULL,
2406		    newchild[c], cb, depth + 2);
2407		free(vname);
2408	}
2409
2410	/*
2411	 * Log device section
2412	 */
2413
2414	if (num_logs(newnv) > 0) {
2415		(void) printf("%-*s      -      -      -      -      -      "
2416		    "-\n", cb->cb_namewidth, "logs");
2417
2418		for (c = 0; c < children; c++) {
2419			uint64_t islog = B_FALSE;
2420			(void) nvlist_lookup_uint64(newchild[c],
2421			    ZPOOL_CONFIG_IS_LOG, &islog);
2422
2423			if (islog) {
2424				vname = zpool_vdev_name(g_zfs, zhp, newchild[c],
2425				    B_FALSE);
2426				print_vdev_stats(zhp, vname, oldnv ?
2427				    oldchild[c] : NULL, newchild[c],
2428				    cb, depth + 2);
2429				free(vname);
2430			}
2431		}
2432
2433	}
2434
2435	/*
2436	 * Include level 2 ARC devices in iostat output
2437	 */
2438	if (nvlist_lookup_nvlist_array(newnv, ZPOOL_CONFIG_L2CACHE,
2439	    &newchild, &children) != 0)
2440		return;
2441
2442	if (oldnv && nvlist_lookup_nvlist_array(oldnv, ZPOOL_CONFIG_L2CACHE,
2443	    &oldchild, &c) != 0)
2444		return;
2445
2446	if (children > 0) {
2447		(void) printf("%-*s      -      -      -      -      -      "
2448		    "-\n", cb->cb_namewidth, "cache");
2449		for (c = 0; c < children; c++) {
2450			vname = zpool_vdev_name(g_zfs, zhp, newchild[c],
2451			    B_FALSE);
2452			print_vdev_stats(zhp, vname, oldnv ? oldchild[c] : NULL,
2453			    newchild[c], cb, depth + 2);
2454			free(vname);
2455		}
2456	}
2457}
2458
2459static int
2460refresh_iostat(zpool_handle_t *zhp, void *data)
2461{
2462	iostat_cbdata_t *cb = data;
2463	boolean_t missing;
2464
2465	/*
2466	 * If the pool has disappeared, remove it from the list and continue.
2467	 */
2468	if (zpool_refresh_stats(zhp, &missing) != 0)
2469		return (-1);
2470
2471	if (missing)
2472		pool_list_remove(cb->cb_list, zhp);
2473
2474	return (0);
2475}
2476
2477/*
2478 * Callback to print out the iostats for the given pool.
2479 */
2480int
2481print_iostat(zpool_handle_t *zhp, void *data)
2482{
2483	iostat_cbdata_t *cb = data;
2484	nvlist_t *oldconfig, *newconfig;
2485	nvlist_t *oldnvroot, *newnvroot;
2486
2487	newconfig = zpool_get_config(zhp, &oldconfig);
2488
2489	if (cb->cb_iteration == 1)
2490		oldconfig = NULL;
2491
2492	verify(nvlist_lookup_nvlist(newconfig, ZPOOL_CONFIG_VDEV_TREE,
2493	    &newnvroot) == 0);
2494
2495	if (oldconfig == NULL)
2496		oldnvroot = NULL;
2497	else
2498		verify(nvlist_lookup_nvlist(oldconfig, ZPOOL_CONFIG_VDEV_TREE,
2499		    &oldnvroot) == 0);
2500
2501	/*
2502	 * Print out the statistics for the pool.
2503	 */
2504	print_vdev_stats(zhp, zpool_get_name(zhp), oldnvroot, newnvroot, cb, 0);
2505
2506	if (cb->cb_verbose)
2507		print_iostat_separator(cb);
2508
2509	return (0);
2510}
2511
2512int
2513get_namewidth(zpool_handle_t *zhp, void *data)
2514{
2515	iostat_cbdata_t *cb = data;
2516	nvlist_t *config, *nvroot;
2517
2518	if ((config = zpool_get_config(zhp, NULL)) != NULL) {
2519		verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE,
2520		    &nvroot) == 0);
2521		if (!cb->cb_verbose)
2522			cb->cb_namewidth = strlen(zpool_get_name(zhp));
2523		else
2524			cb->cb_namewidth = max_width(zhp, nvroot, 0,
2525			    cb->cb_namewidth);
2526	}
2527
2528	/*
2529	 * The width must fall into the range [10,38].  The upper limit is the
2530	 * maximum we can have and still fit in 80 columns.
2531	 */
2532	if (cb->cb_namewidth < 10)
2533		cb->cb_namewidth = 10;
2534	if (cb->cb_namewidth > 38)
2535		cb->cb_namewidth = 38;
2536
2537	return (0);
2538}
2539
2540/*
2541 * Parse the input string, get the 'interval' and 'count' value if there is one.
2542 */
2543static void
2544get_interval_count(int *argcp, char **argv, unsigned long *iv,
2545    unsigned long *cnt)
2546{
2547	unsigned long interval = 0, count = 0;
2548	int argc = *argcp, errno;
2549
2550	/*
2551	 * Determine if the last argument is an integer or a pool name
2552	 */
2553	if (argc > 0 && isdigit(argv[argc - 1][0])) {
2554		char *end;
2555
2556		errno = 0;
2557		interval = strtoul(argv[argc - 1], &end, 10);
2558
2559		if (*end == '\0' && errno == 0) {
2560			if (interval == 0) {
2561				(void) fprintf(stderr, gettext("interval "
2562				    "cannot be zero\n"));
2563				usage(B_FALSE);
2564			}
2565			/*
2566			 * Ignore the last parameter
2567			 */
2568			argc--;
2569		} else {
2570			/*
2571			 * If this is not a valid number, just plow on.  The
2572			 * user will get a more informative error message later
2573			 * on.
2574			 */
2575			interval = 0;
2576		}
2577	}
2578
2579	/*
2580	 * If the last argument is also an integer, then we have both a count
2581	 * and an interval.
2582	 */
2583	if (argc > 0 && isdigit(argv[argc - 1][0])) {
2584		char *end;
2585
2586		errno = 0;
2587		count = interval;
2588		interval = strtoul(argv[argc - 1], &end, 10);
2589
2590		if (*end == '\0' && errno == 0) {
2591			if (interval == 0) {
2592				(void) fprintf(stderr, gettext("interval "
2593				    "cannot be zero\n"));
2594				usage(B_FALSE);
2595			}
2596
2597			/*
2598			 * Ignore the last parameter
2599			 */
2600			argc--;
2601		} else {
2602			interval = 0;
2603		}
2604	}
2605
2606	*iv = interval;
2607	*cnt = count;
2608	*argcp = argc;
2609}
2610
2611static void
2612get_timestamp_arg(char c)
2613{
2614	if (c == 'u')
2615		timestamp_fmt = UDATE;
2616	else if (c == 'd')
2617		timestamp_fmt = DDATE;
2618	else
2619		usage(B_FALSE);
2620}
2621
2622/*
2623 * zpool iostat [-v] [-T d|u] [pool] ... [interval [count]]
2624 *
2625 *	-v	Display statistics for individual vdevs
2626 *	-T	Display a timestamp in date(1) or Unix format
2627 *
2628 * This command can be tricky because we want to be able to deal with pool
2629 * creation/destruction as well as vdev configuration changes.  The bulk of this
2630 * processing is handled by the pool_list_* routines in zpool_iter.c.  We rely
2631 * on pool_list_update() to detect the addition of new pools.  Configuration
2632 * changes are all handled within libzfs.
2633 */
2634int
2635zpool_do_iostat(int argc, char **argv)
2636{
2637	int c;
2638	int ret;
2639	int npools;
2640	unsigned long interval = 0, count = 0;
2641	zpool_list_t *list;
2642	boolean_t verbose = B_FALSE;
2643	iostat_cbdata_t cb;
2644
2645	/* check options */
2646	while ((c = getopt(argc, argv, "T:v")) != -1) {
2647		switch (c) {
2648		case 'T':
2649			get_timestamp_arg(*optarg);
2650			break;
2651		case 'v':
2652			verbose = B_TRUE;
2653			break;
2654		case '?':
2655			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
2656			    optopt);
2657			usage(B_FALSE);
2658		}
2659	}
2660
2661	argc -= optind;
2662	argv += optind;
2663
2664	get_interval_count(&argc, argv, &interval, &count);
2665
2666	/*
2667	 * Construct the list of all interesting pools.
2668	 */
2669	ret = 0;
2670	if ((list = pool_list_get(argc, argv, NULL, &ret)) == NULL)
2671		return (1);
2672
2673	if (pool_list_count(list) == 0 && argc != 0) {
2674		pool_list_free(list);
2675		return (1);
2676	}
2677
2678	if (pool_list_count(list) == 0 && interval == 0) {
2679		pool_list_free(list);
2680		(void) fprintf(stderr, gettext("no pools available\n"));
2681		return (1);
2682	}
2683
2684	/*
2685	 * Enter the main iostat loop.
2686	 */
2687	cb.cb_list = list;
2688	cb.cb_verbose = verbose;
2689	cb.cb_iteration = 0;
2690	cb.cb_namewidth = 0;
2691
2692	for (;;) {
2693		pool_list_update(list);
2694
2695		if ((npools = pool_list_count(list)) == 0)
2696			break;
2697
2698		/*
2699		 * Refresh all statistics.  This is done as an explicit step
2700		 * before calculating the maximum name width, so that any
2701		 * configuration changes are properly accounted for.
2702		 */
2703		(void) pool_list_iter(list, B_FALSE, refresh_iostat, &cb);
2704
2705		/*
2706		 * Iterate over all pools to determine the maximum width
2707		 * for the pool / device name column across all pools.
2708		 */
2709		cb.cb_namewidth = 0;
2710		(void) pool_list_iter(list, B_FALSE, get_namewidth, &cb);
2711
2712		if (timestamp_fmt != NODATE)
2713			print_timestamp(timestamp_fmt);
2714
2715		/*
2716		 * If it's the first time, or verbose mode, print the header.
2717		 */
2718		if (++cb.cb_iteration == 1 || verbose)
2719			print_iostat_header(&cb);
2720
2721		(void) pool_list_iter(list, B_FALSE, print_iostat, &cb);
2722
2723		/*
2724		 * If there's more than one pool, and we're not in verbose mode
2725		 * (which prints a separator for us), then print a separator.
2726		 */
2727		if (npools > 1 && !verbose)
2728			print_iostat_separator(&cb);
2729
2730		if (verbose)
2731			(void) printf("\n");
2732
2733		/*
2734		 * Flush the output so that redirection to a file isn't buffered
2735		 * indefinitely.
2736		 */
2737		(void) fflush(stdout);
2738
2739		if (interval == 0)
2740			break;
2741
2742		if (count != 0 && --count == 0)
2743			break;
2744
2745		(void) sleep(interval);
2746	}
2747
2748	pool_list_free(list);
2749
2750	return (ret);
2751}
2752
2753typedef struct list_cbdata {
2754	boolean_t	cb_verbose;
2755	int		cb_namewidth;
2756	boolean_t	cb_scripted;
2757	zprop_list_t	*cb_proplist;
2758	boolean_t	cb_literal;
2759} list_cbdata_t;
2760
2761/*
2762 * Given a list of columns to display, output appropriate headers for each one.
2763 */
2764static void
2765print_header(list_cbdata_t *cb)
2766{
2767	zprop_list_t *pl = cb->cb_proplist;
2768	char headerbuf[ZPOOL_MAXPROPLEN];
2769	const char *header;
2770	boolean_t first = B_TRUE;
2771	boolean_t right_justify;
2772	size_t width = 0;
2773
2774	for (; pl != NULL; pl = pl->pl_next) {
2775		width = pl->pl_width;
2776		if (first && cb->cb_verbose) {
2777			/*
2778			 * Reset the width to accommodate the verbose listing
2779			 * of devices.
2780			 */
2781			width = cb->cb_namewidth;
2782		}
2783
2784		if (!first)
2785			(void) printf("  ");
2786		else
2787			first = B_FALSE;
2788
2789		right_justify = B_FALSE;
2790		if (pl->pl_prop != ZPROP_INVAL) {
2791			header = zpool_prop_column_name(pl->pl_prop);
2792			right_justify = zpool_prop_align_right(pl->pl_prop);
2793		} else {
2794			int i;
2795
2796			for (i = 0; pl->pl_user_prop[i] != '\0'; i++)
2797				headerbuf[i] = toupper(pl->pl_user_prop[i]);
2798			headerbuf[i] = '\0';
2799			header = headerbuf;
2800		}
2801
2802		if (pl->pl_next == NULL && !right_justify)
2803			(void) printf("%s", header);
2804		else if (right_justify)
2805			(void) printf("%*s", width, header);
2806		else
2807			(void) printf("%-*s", width, header);
2808
2809	}
2810
2811	(void) printf("\n");
2812}
2813
2814/*
2815 * Given a pool and a list of properties, print out all the properties according
2816 * to the described layout.
2817 */
2818static void
2819print_pool(zpool_handle_t *zhp, list_cbdata_t *cb)
2820{
2821	zprop_list_t *pl = cb->cb_proplist;
2822	boolean_t first = B_TRUE;
2823	char property[ZPOOL_MAXPROPLEN];
2824	char *propstr;
2825	boolean_t right_justify;
2826	size_t width;
2827
2828	for (; pl != NULL; pl = pl->pl_next) {
2829
2830		width = pl->pl_width;
2831		if (first && cb->cb_verbose) {
2832			/*
2833			 * Reset the width to accommodate the verbose listing
2834			 * of devices.
2835			 */
2836			width = cb->cb_namewidth;
2837		}
2838
2839		if (!first) {
2840			if (cb->cb_scripted)
2841				(void) printf("\t");
2842			else
2843				(void) printf("  ");
2844		} else {
2845			first = B_FALSE;
2846		}
2847
2848		right_justify = B_FALSE;
2849		if (pl->pl_prop != ZPROP_INVAL) {
2850			if (pl->pl_prop == ZPOOL_PROP_EXPANDSZ &&
2851			    zpool_get_prop_int(zhp, pl->pl_prop, NULL) == 0)
2852				propstr = "-";
2853			else if (zpool_get_prop(zhp, pl->pl_prop, property,
2854			    sizeof (property), NULL, cb->cb_literal) != 0)
2855				propstr = "-";
2856			else
2857				propstr = property;
2858
2859			right_justify = zpool_prop_align_right(pl->pl_prop);
2860		} else if ((zpool_prop_feature(pl->pl_user_prop) ||
2861		    zpool_prop_unsupported(pl->pl_user_prop)) &&
2862		    zpool_prop_get_feature(zhp, pl->pl_user_prop, property,
2863		    sizeof (property)) == 0) {
2864			propstr = property;
2865		} else {
2866			propstr = "-";
2867		}
2868
2869
2870		/*
2871		 * If this is being called in scripted mode, or if this is the
2872		 * last column and it is left-justified, don't include a width
2873		 * format specifier.
2874		 */
2875		if (cb->cb_scripted || (pl->pl_next == NULL && !right_justify))
2876			(void) printf("%s", propstr);
2877		else if (right_justify)
2878			(void) printf("%*s", width, propstr);
2879		else
2880			(void) printf("%-*s", width, propstr);
2881	}
2882
2883	(void) printf("\n");
2884}
2885
2886static void
2887print_one_column(zpool_prop_t prop, uint64_t value, boolean_t scripted)
2888{
2889	char propval[64];
2890	boolean_t fixed;
2891	size_t width = zprop_width(prop, &fixed, ZFS_TYPE_POOL);
2892
2893	zfs_nicenum(value, propval, sizeof (propval));
2894
2895	if (prop == ZPOOL_PROP_EXPANDSZ && value == 0)
2896		(void) strlcpy(propval, "-", sizeof (propval));
2897
2898	if (scripted)
2899		(void) printf("\t%s", propval);
2900	else
2901		(void) printf("  %*s", width, propval);
2902}
2903
2904void
2905print_list_stats(zpool_handle_t *zhp, const char *name, nvlist_t *nv,
2906    list_cbdata_t *cb, int depth)
2907{
2908	nvlist_t **child;
2909	vdev_stat_t *vs;
2910	uint_t c, children;
2911	char *vname;
2912	boolean_t scripted = cb->cb_scripted;
2913
2914	verify(nvlist_lookup_uint64_array(nv, ZPOOL_CONFIG_VDEV_STATS,
2915	    (uint64_t **)&vs, &c) == 0);
2916
2917	if (name != NULL) {
2918		if (scripted)
2919			(void) printf("\t%s", name);
2920		else if (strlen(name) + depth > cb->cb_namewidth)
2921			(void) printf("%*s%s", depth, "", name);
2922		else
2923			(void) printf("%*s%s%*s", depth, "", name,
2924			    (int)(cb->cb_namewidth - strlen(name) - depth), "");
2925
2926		/* only toplevel vdevs have capacity stats */
2927		if (vs->vs_space == 0) {
2928			if (scripted)
2929				(void) printf("\t-\t-\t-");
2930			else
2931				(void) printf("      -      -      -");
2932		} else {
2933			print_one_column(ZPOOL_PROP_SIZE, vs->vs_space,
2934			    scripted);
2935			print_one_column(ZPOOL_PROP_CAPACITY, vs->vs_alloc,
2936			    scripted);
2937			print_one_column(ZPOOL_PROP_FREE,
2938			    vs->vs_space - vs->vs_alloc, scripted);
2939		}
2940		print_one_column(ZPOOL_PROP_EXPANDSZ, vs->vs_esize,
2941		    scripted);
2942		(void) printf("\n");
2943	}
2944
2945	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
2946	    &child, &children) != 0)
2947		return;
2948
2949	for (c = 0; c < children; c++) {
2950		uint64_t ishole = B_FALSE;
2951
2952		if (nvlist_lookup_uint64(child[c],
2953		    ZPOOL_CONFIG_IS_HOLE, &ishole) == 0 && ishole)
2954			continue;
2955
2956		vname = zpool_vdev_name(g_zfs, zhp, child[c], B_FALSE);
2957		print_list_stats(zhp, vname, child[c], cb, depth + 2);
2958		free(vname);
2959	}
2960
2961	/*
2962	 * Include level 2 ARC devices in iostat output
2963	 */
2964	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_L2CACHE,
2965	    &child, &children) != 0)
2966		return;
2967
2968	if (children > 0) {
2969		(void) printf("%-*s      -      -      -      -      -      "
2970		    "-\n", cb->cb_namewidth, "cache");
2971		for (c = 0; c < children; c++) {
2972			vname = zpool_vdev_name(g_zfs, zhp, child[c],
2973			    B_FALSE);
2974			print_list_stats(zhp, vname, child[c], cb, depth + 2);
2975			free(vname);
2976		}
2977	}
2978}
2979
2980
2981/*
2982 * Generic callback function to list a pool.
2983 */
2984int
2985list_callback(zpool_handle_t *zhp, void *data)
2986{
2987	list_cbdata_t *cbp = data;
2988	nvlist_t *config;
2989	nvlist_t *nvroot;
2990
2991	config = zpool_get_config(zhp, NULL);
2992
2993	print_pool(zhp, cbp);
2994	if (!cbp->cb_verbose)
2995		return (0);
2996
2997	verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE,
2998	    &nvroot) == 0);
2999	print_list_stats(zhp, NULL, nvroot, cbp, 0);
3000
3001	return (0);
3002}
3003
3004/*
3005 * zpool list [-Hp] [-o prop[,prop]*] [-T d|u] [pool] ... [interval [count]]
3006 *
3007 *	-H	Scripted mode.  Don't display headers, and separate properties
3008 *		by a single tab.
3009 *	-o	List of properties to display.  Defaults to
3010 *		"name,size,allocated,free,capacity,health,altroot"
3011 * 	-p	Diplay values in parsable (exact) format.
3012 *	-T	Display a timestamp in date(1) or Unix format
3013 *
3014 * List all pools in the system, whether or not they're healthy.  Output space
3015 * statistics for each one, as well as health status summary.
3016 */
3017int
3018zpool_do_list(int argc, char **argv)
3019{
3020	int c;
3021	int ret;
3022	list_cbdata_t cb = { 0 };
3023	static char default_props[] =
3024	    "name,size,allocated,free,capacity,dedupratio,"
3025	    "health,altroot";
3026	char *props = default_props;
3027	unsigned long interval = 0, count = 0;
3028	zpool_list_t *list;
3029	boolean_t first = B_TRUE;
3030
3031	/* check options */
3032	while ((c = getopt(argc, argv, ":Ho:pT:v")) != -1) {
3033		switch (c) {
3034		case 'H':
3035			cb.cb_scripted = B_TRUE;
3036			break;
3037		case 'o':
3038			props = optarg;
3039			break;
3040		case 'p':
3041			cb.cb_literal = B_TRUE;
3042			break;
3043		case 'T':
3044			get_timestamp_arg(*optarg);
3045			break;
3046		case 'v':
3047			cb.cb_verbose = B_TRUE;
3048			break;
3049		case ':':
3050			(void) fprintf(stderr, gettext("missing argument for "
3051			    "'%c' option\n"), optopt);
3052			usage(B_FALSE);
3053			break;
3054		case '?':
3055			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3056			    optopt);
3057			usage(B_FALSE);
3058		}
3059	}
3060
3061	argc -= optind;
3062	argv += optind;
3063
3064	get_interval_count(&argc, argv, &interval, &count);
3065
3066	if (zprop_get_list(g_zfs, props, &cb.cb_proplist, ZFS_TYPE_POOL) != 0)
3067		usage(B_FALSE);
3068
3069	if ((list = pool_list_get(argc, argv, &cb.cb_proplist, &ret)) == NULL)
3070		return (1);
3071
3072	if (argc == 0 && !cb.cb_scripted && pool_list_count(list) == 0) {
3073		(void) printf(gettext("no pools available\n"));
3074		zprop_free_list(cb.cb_proplist);
3075		return (0);
3076	}
3077
3078	for (;;) {
3079		pool_list_update(list);
3080
3081		if (pool_list_count(list) == 0)
3082			break;
3083
3084		cb.cb_namewidth = 0;
3085		(void) pool_list_iter(list, B_FALSE, get_namewidth, &cb);
3086
3087		if (timestamp_fmt != NODATE)
3088			print_timestamp(timestamp_fmt);
3089
3090		if (!cb.cb_scripted && (first || cb.cb_verbose)) {
3091			print_header(&cb);
3092			first = B_FALSE;
3093		}
3094		ret = pool_list_iter(list, B_TRUE, list_callback, &cb);
3095
3096		if (interval == 0)
3097			break;
3098
3099		if (count != 0 && --count == 0)
3100			break;
3101
3102		(void) sleep(interval);
3103	}
3104
3105	zprop_free_list(cb.cb_proplist);
3106	return (ret);
3107}
3108
3109static nvlist_t *
3110zpool_get_vdev_by_name(nvlist_t *nv, char *name)
3111{
3112	nvlist_t **child;
3113	uint_t c, children;
3114	nvlist_t *match;
3115	char *path;
3116
3117	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
3118	    &child, &children) != 0) {
3119		verify(nvlist_lookup_string(nv, ZPOOL_CONFIG_PATH, &path) == 0);
3120		if (strncmp(name, _PATH_DEV, sizeof(_PATH_DEV) - 1) == 0)
3121			name += sizeof(_PATH_DEV) - 1;
3122		if (strncmp(path, _PATH_DEV, sizeof(_PATH_DEV) - 1) == 0)
3123			path += sizeof(_PATH_DEV) - 1;
3124		if (strcmp(name, path) == 0)
3125			return (nv);
3126		return (NULL);
3127	}
3128
3129	for (c = 0; c < children; c++)
3130		if ((match = zpool_get_vdev_by_name(child[c], name)) != NULL)
3131			return (match);
3132
3133	return (NULL);
3134}
3135
3136static int
3137zpool_do_attach_or_replace(int argc, char **argv, int replacing)
3138{
3139	boolean_t force = B_FALSE;
3140	int c;
3141	nvlist_t *nvroot;
3142	char *poolname, *old_disk, *new_disk;
3143	zpool_handle_t *zhp;
3144	int ret;
3145
3146	/* check options */
3147	while ((c = getopt(argc, argv, "f")) != -1) {
3148		switch (c) {
3149		case 'f':
3150			force = B_TRUE;
3151			break;
3152		case '?':
3153			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3154			    optopt);
3155			usage(B_FALSE);
3156		}
3157	}
3158
3159	argc -= optind;
3160	argv += optind;
3161
3162	/* get pool name and check number of arguments */
3163	if (argc < 1) {
3164		(void) fprintf(stderr, gettext("missing pool name argument\n"));
3165		usage(B_FALSE);
3166	}
3167
3168	poolname = argv[0];
3169
3170	if (argc < 2) {
3171		(void) fprintf(stderr,
3172		    gettext("missing <device> specification\n"));
3173		usage(B_FALSE);
3174	}
3175
3176	old_disk = argv[1];
3177
3178	if (argc < 3) {
3179		if (!replacing) {
3180			(void) fprintf(stderr,
3181			    gettext("missing <new_device> specification\n"));
3182			usage(B_FALSE);
3183		}
3184		new_disk = old_disk;
3185		argc -= 1;
3186		argv += 1;
3187	} else {
3188		new_disk = argv[2];
3189		argc -= 2;
3190		argv += 2;
3191	}
3192
3193	if (argc > 1) {
3194		(void) fprintf(stderr, gettext("too many arguments\n"));
3195		usage(B_FALSE);
3196	}
3197
3198	if ((zhp = zpool_open(g_zfs, poolname)) == NULL)
3199		return (1);
3200
3201	if (zpool_get_config(zhp, NULL) == NULL) {
3202		(void) fprintf(stderr, gettext("pool '%s' is unavailable\n"),
3203		    poolname);
3204		zpool_close(zhp);
3205		return (1);
3206	}
3207
3208	nvroot = make_root_vdev(zhp, force, B_FALSE, replacing, B_FALSE,
3209	    argc, argv);
3210	if (nvroot == NULL) {
3211		zpool_close(zhp);
3212		return (1);
3213	}
3214
3215	ret = zpool_vdev_attach(zhp, old_disk, new_disk, nvroot, replacing);
3216
3217	nvlist_free(nvroot);
3218	zpool_close(zhp);
3219
3220	return (ret);
3221}
3222
3223/*
3224 * zpool replace [-f] <pool> <device> <new_device>
3225 *
3226 *	-f	Force attach, even if <new_device> appears to be in use.
3227 *
3228 * Replace <device> with <new_device>.
3229 */
3230/* ARGSUSED */
3231int
3232zpool_do_replace(int argc, char **argv)
3233{
3234	return (zpool_do_attach_or_replace(argc, argv, B_TRUE));
3235}
3236
3237/*
3238 * zpool attach [-f] <pool> <device> <new_device>
3239 *
3240 *	-f	Force attach, even if <new_device> appears to be in use.
3241 *
3242 * Attach <new_device> to the mirror containing <device>.  If <device> is not
3243 * part of a mirror, then <device> will be transformed into a mirror of
3244 * <device> and <new_device>.  In either case, <new_device> will begin life
3245 * with a DTL of [0, now], and will immediately begin to resilver itself.
3246 */
3247int
3248zpool_do_attach(int argc, char **argv)
3249{
3250	return (zpool_do_attach_or_replace(argc, argv, B_FALSE));
3251}
3252
3253/*
3254 * zpool detach [-f] <pool> <device>
3255 *
3256 *	-f	Force detach of <device>, even if DTLs argue against it
3257 *		(not supported yet)
3258 *
3259 * Detach a device from a mirror.  The operation will be refused if <device>
3260 * is the last device in the mirror, or if the DTLs indicate that this device
3261 * has the only valid copy of some data.
3262 */
3263/* ARGSUSED */
3264int
3265zpool_do_detach(int argc, char **argv)
3266{
3267	int c;
3268	char *poolname, *path;
3269	zpool_handle_t *zhp;
3270	int ret;
3271
3272	/* check options */
3273	while ((c = getopt(argc, argv, "f")) != -1) {
3274		switch (c) {
3275		case 'f':
3276		case '?':
3277			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3278			    optopt);
3279			usage(B_FALSE);
3280		}
3281	}
3282
3283	argc -= optind;
3284	argv += optind;
3285
3286	/* get pool name and check number of arguments */
3287	if (argc < 1) {
3288		(void) fprintf(stderr, gettext("missing pool name argument\n"));
3289		usage(B_FALSE);
3290	}
3291
3292	if (argc < 2) {
3293		(void) fprintf(stderr,
3294		    gettext("missing <device> specification\n"));
3295		usage(B_FALSE);
3296	}
3297
3298	poolname = argv[0];
3299	path = argv[1];
3300
3301	if ((zhp = zpool_open(g_zfs, poolname)) == NULL)
3302		return (1);
3303
3304	ret = zpool_vdev_detach(zhp, path);
3305
3306	zpool_close(zhp);
3307
3308	return (ret);
3309}
3310
3311/*
3312 * zpool split [-n] [-o prop=val] ...
3313 *		[-o mntopt] ...
3314 *		[-R altroot] <pool> <newpool> [<device> ...]
3315 *
3316 *	-n	Do not split the pool, but display the resulting layout if
3317 *		it were to be split.
3318 *	-o	Set property=value, or set mount options.
3319 *	-R	Mount the split-off pool under an alternate root.
3320 *
3321 * Splits the named pool and gives it the new pool name.  Devices to be split
3322 * off may be listed, provided that no more than one device is specified
3323 * per top-level vdev mirror.  The newly split pool is left in an exported
3324 * state unless -R is specified.
3325 *
3326 * Restrictions: the top-level of the pool pool must only be made up of
3327 * mirrors; all devices in the pool must be healthy; no device may be
3328 * undergoing a resilvering operation.
3329 */
3330int
3331zpool_do_split(int argc, char **argv)
3332{
3333	char *srcpool, *newpool, *propval;
3334	char *mntopts = NULL;
3335	splitflags_t flags;
3336	int c, ret = 0;
3337	zpool_handle_t *zhp;
3338	nvlist_t *config, *props = NULL;
3339
3340	flags.dryrun = B_FALSE;
3341	flags.import = B_FALSE;
3342
3343	/* check options */
3344	while ((c = getopt(argc, argv, ":R:no:")) != -1) {
3345		switch (c) {
3346		case 'R':
3347			flags.import = B_TRUE;
3348			if (add_prop_list(
3349			    zpool_prop_to_name(ZPOOL_PROP_ALTROOT), optarg,
3350			    &props, B_TRUE) != 0) {
3351				if (props)
3352					nvlist_free(props);
3353				usage(B_FALSE);
3354			}
3355			break;
3356		case 'n':
3357			flags.dryrun = B_TRUE;
3358			break;
3359		case 'o':
3360			if ((propval = strchr(optarg, '=')) != NULL) {
3361				*propval = '\0';
3362				propval++;
3363				if (add_prop_list(optarg, propval,
3364				    &props, B_TRUE) != 0) {
3365					if (props)
3366						nvlist_free(props);
3367					usage(B_FALSE);
3368				}
3369			} else {
3370				mntopts = optarg;
3371			}
3372			break;
3373		case ':':
3374			(void) fprintf(stderr, gettext("missing argument for "
3375			    "'%c' option\n"), optopt);
3376			usage(B_FALSE);
3377			break;
3378		case '?':
3379			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3380			    optopt);
3381			usage(B_FALSE);
3382			break;
3383		}
3384	}
3385
3386	if (!flags.import && mntopts != NULL) {
3387		(void) fprintf(stderr, gettext("setting mntopts is only "
3388		    "valid when importing the pool\n"));
3389		usage(B_FALSE);
3390	}
3391
3392	argc -= optind;
3393	argv += optind;
3394
3395	if (argc < 1) {
3396		(void) fprintf(stderr, gettext("Missing pool name\n"));
3397		usage(B_FALSE);
3398	}
3399	if (argc < 2) {
3400		(void) fprintf(stderr, gettext("Missing new pool name\n"));
3401		usage(B_FALSE);
3402	}
3403
3404	srcpool = argv[0];
3405	newpool = argv[1];
3406
3407	argc -= 2;
3408	argv += 2;
3409
3410	if ((zhp = zpool_open(g_zfs, srcpool)) == NULL)
3411		return (1);
3412
3413	config = split_mirror_vdev(zhp, newpool, props, flags, argc, argv);
3414	if (config == NULL) {
3415		ret = 1;
3416	} else {
3417		if (flags.dryrun) {
3418			(void) printf(gettext("would create '%s' with the "
3419			    "following layout:\n\n"), newpool);
3420			print_vdev_tree(NULL, newpool, config, 0, B_FALSE);
3421		}
3422		nvlist_free(config);
3423	}
3424
3425	zpool_close(zhp);
3426
3427	if (ret != 0 || flags.dryrun || !flags.import)
3428		return (ret);
3429
3430	/*
3431	 * The split was successful. Now we need to open the new
3432	 * pool and import it.
3433	 */
3434	if ((zhp = zpool_open_canfail(g_zfs, newpool)) == NULL)
3435		return (1);
3436	if (zpool_get_state(zhp) != POOL_STATE_UNAVAIL &&
3437	    zpool_enable_datasets(zhp, mntopts, 0) != 0) {
3438		ret = 1;
3439		(void) fprintf(stderr, gettext("Split was successful, but "
3440		    "the datasets could not all be mounted\n"));
3441		(void) fprintf(stderr, gettext("Try doing '%s' with a "
3442		    "different altroot\n"), "zpool import");
3443	}
3444	zpool_close(zhp);
3445
3446	return (ret);
3447}
3448
3449
3450
3451/*
3452 * zpool online <pool> <device> ...
3453 */
3454int
3455zpool_do_online(int argc, char **argv)
3456{
3457	int c, i;
3458	char *poolname;
3459	zpool_handle_t *zhp;
3460	int ret = 0;
3461	vdev_state_t newstate;
3462	int flags = 0;
3463
3464	/* check options */
3465	while ((c = getopt(argc, argv, "et")) != -1) {
3466		switch (c) {
3467		case 'e':
3468			flags |= ZFS_ONLINE_EXPAND;
3469			break;
3470		case 't':
3471		case '?':
3472			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3473			    optopt);
3474			usage(B_FALSE);
3475		}
3476	}
3477
3478	argc -= optind;
3479	argv += optind;
3480
3481	/* get pool name and check number of arguments */
3482	if (argc < 1) {
3483		(void) fprintf(stderr, gettext("missing pool name\n"));
3484		usage(B_FALSE);
3485	}
3486	if (argc < 2) {
3487		(void) fprintf(stderr, gettext("missing device name\n"));
3488		usage(B_FALSE);
3489	}
3490
3491	poolname = argv[0];
3492
3493	if ((zhp = zpool_open(g_zfs, poolname)) == NULL)
3494		return (1);
3495
3496	for (i = 1; i < argc; i++) {
3497		if (zpool_vdev_online(zhp, argv[i], flags, &newstate) == 0) {
3498			if (newstate != VDEV_STATE_HEALTHY) {
3499				(void) printf(gettext("warning: device '%s' "
3500				    "onlined, but remains in faulted state\n"),
3501				    argv[i]);
3502				if (newstate == VDEV_STATE_FAULTED)
3503					(void) printf(gettext("use 'zpool "
3504					    "clear' to restore a faulted "
3505					    "device\n"));
3506				else
3507					(void) printf(gettext("use 'zpool "
3508					    "replace' to replace devices "
3509					    "that are no longer present\n"));
3510			}
3511		} else {
3512			ret = 1;
3513		}
3514	}
3515
3516	zpool_close(zhp);
3517
3518	return (ret);
3519}
3520
3521/*
3522 * zpool offline [-ft] <pool> <device> ...
3523 *
3524 *	-f	Force the device into the offline state, even if doing
3525 *		so would appear to compromise pool availability.
3526 *		(not supported yet)
3527 *
3528 *	-t	Only take the device off-line temporarily.  The offline
3529 *		state will not be persistent across reboots.
3530 */
3531/* ARGSUSED */
3532int
3533zpool_do_offline(int argc, char **argv)
3534{
3535	int c, i;
3536	char *poolname;
3537	zpool_handle_t *zhp;
3538	int ret = 0;
3539	boolean_t istmp = B_FALSE;
3540
3541	/* check options */
3542	while ((c = getopt(argc, argv, "ft")) != -1) {
3543		switch (c) {
3544		case 't':
3545			istmp = B_TRUE;
3546			break;
3547		case 'f':
3548		case '?':
3549			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3550			    optopt);
3551			usage(B_FALSE);
3552		}
3553	}
3554
3555	argc -= optind;
3556	argv += optind;
3557
3558	/* get pool name and check number of arguments */
3559	if (argc < 1) {
3560		(void) fprintf(stderr, gettext("missing pool name\n"));
3561		usage(B_FALSE);
3562	}
3563	if (argc < 2) {
3564		(void) fprintf(stderr, gettext("missing device name\n"));
3565		usage(B_FALSE);
3566	}
3567
3568	poolname = argv[0];
3569
3570	if ((zhp = zpool_open(g_zfs, poolname)) == NULL)
3571		return (1);
3572
3573	for (i = 1; i < argc; i++) {
3574		if (zpool_vdev_offline(zhp, argv[i], istmp) != 0)
3575			ret = 1;
3576	}
3577
3578	zpool_close(zhp);
3579
3580	return (ret);
3581}
3582
3583/*
3584 * zpool clear <pool> [device]
3585 *
3586 * Clear all errors associated with a pool or a particular device.
3587 */
3588int
3589zpool_do_clear(int argc, char **argv)
3590{
3591	int c;
3592	int ret = 0;
3593	boolean_t dryrun = B_FALSE;
3594	boolean_t do_rewind = B_FALSE;
3595	boolean_t xtreme_rewind = B_FALSE;
3596	uint32_t rewind_policy = ZPOOL_NO_REWIND;
3597	nvlist_t *policy = NULL;
3598	zpool_handle_t *zhp;
3599	char *pool, *device;
3600
3601	/* check options */
3602	while ((c = getopt(argc, argv, "FnX")) != -1) {
3603		switch (c) {
3604		case 'F':
3605			do_rewind = B_TRUE;
3606			break;
3607		case 'n':
3608			dryrun = B_TRUE;
3609			break;
3610		case 'X':
3611			xtreme_rewind = B_TRUE;
3612			break;
3613		case '?':
3614			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3615			    optopt);
3616			usage(B_FALSE);
3617		}
3618	}
3619
3620	argc -= optind;
3621	argv += optind;
3622
3623	if (argc < 1) {
3624		(void) fprintf(stderr, gettext("missing pool name\n"));
3625		usage(B_FALSE);
3626	}
3627
3628	if (argc > 2) {
3629		(void) fprintf(stderr, gettext("too many arguments\n"));
3630		usage(B_FALSE);
3631	}
3632
3633	if ((dryrun || xtreme_rewind) && !do_rewind) {
3634		(void) fprintf(stderr,
3635		    gettext("-n or -X only meaningful with -F\n"));
3636		usage(B_FALSE);
3637	}
3638	if (dryrun)
3639		rewind_policy = ZPOOL_TRY_REWIND;
3640	else if (do_rewind)
3641		rewind_policy = ZPOOL_DO_REWIND;
3642	if (xtreme_rewind)
3643		rewind_policy |= ZPOOL_EXTREME_REWIND;
3644
3645	/* In future, further rewind policy choices can be passed along here */
3646	if (nvlist_alloc(&policy, NV_UNIQUE_NAME, 0) != 0 ||
3647	    nvlist_add_uint32(policy, ZPOOL_REWIND_REQUEST, rewind_policy) != 0)
3648		return (1);
3649
3650	pool = argv[0];
3651	device = argc == 2 ? argv[1] : NULL;
3652
3653	if ((zhp = zpool_open_canfail(g_zfs, pool)) == NULL) {
3654		nvlist_free(policy);
3655		return (1);
3656	}
3657
3658	if (zpool_clear(zhp, device, policy) != 0)
3659		ret = 1;
3660
3661	zpool_close(zhp);
3662
3663	nvlist_free(policy);
3664
3665	return (ret);
3666}
3667
3668/*
3669 * zpool reguid <pool>
3670 */
3671int
3672zpool_do_reguid(int argc, char **argv)
3673{
3674	int c;
3675	char *poolname;
3676	zpool_handle_t *zhp;
3677	int ret = 0;
3678
3679	/* check options */
3680	while ((c = getopt(argc, argv, "")) != -1) {
3681		switch (c) {
3682		case '?':
3683			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3684			    optopt);
3685			usage(B_FALSE);
3686		}
3687	}
3688
3689	argc -= optind;
3690	argv += optind;
3691
3692	/* get pool name and check number of arguments */
3693	if (argc < 1) {
3694		(void) fprintf(stderr, gettext("missing pool name\n"));
3695		usage(B_FALSE);
3696	}
3697
3698	if (argc > 1) {
3699		(void) fprintf(stderr, gettext("too many arguments\n"));
3700		usage(B_FALSE);
3701	}
3702
3703	poolname = argv[0];
3704	if ((zhp = zpool_open(g_zfs, poolname)) == NULL)
3705		return (1);
3706
3707	ret = zpool_reguid(zhp);
3708
3709	zpool_close(zhp);
3710	return (ret);
3711}
3712
3713
3714/*
3715 * zpool reopen <pool>
3716 *
3717 * Reopen the pool so that the kernel can update the sizes of all vdevs.
3718 */
3719int
3720zpool_do_reopen(int argc, char **argv)
3721{
3722	int c;
3723	int ret = 0;
3724	zpool_handle_t *zhp;
3725	char *pool;
3726
3727	/* check options */
3728	while ((c = getopt(argc, argv, "")) != -1) {
3729		switch (c) {
3730		case '?':
3731			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3732			    optopt);
3733			usage(B_FALSE);
3734		}
3735	}
3736
3737	argc--;
3738	argv++;
3739
3740	if (argc < 1) {
3741		(void) fprintf(stderr, gettext("missing pool name\n"));
3742		usage(B_FALSE);
3743	}
3744
3745	if (argc > 1) {
3746		(void) fprintf(stderr, gettext("too many arguments\n"));
3747		usage(B_FALSE);
3748	}
3749
3750	pool = argv[0];
3751	if ((zhp = zpool_open_canfail(g_zfs, pool)) == NULL)
3752		return (1);
3753
3754	ret = zpool_reopen(zhp);
3755	zpool_close(zhp);
3756	return (ret);
3757}
3758
3759typedef struct scrub_cbdata {
3760	int	cb_type;
3761	int	cb_argc;
3762	char	**cb_argv;
3763} scrub_cbdata_t;
3764
3765int
3766scrub_callback(zpool_handle_t *zhp, void *data)
3767{
3768	scrub_cbdata_t *cb = data;
3769	int err;
3770
3771	/*
3772	 * Ignore faulted pools.
3773	 */
3774	if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) {
3775		(void) fprintf(stderr, gettext("cannot scrub '%s': pool is "
3776		    "currently unavailable\n"), zpool_get_name(zhp));
3777		return (1);
3778	}
3779
3780	err = zpool_scan(zhp, cb->cb_type);
3781
3782	return (err != 0);
3783}
3784
3785/*
3786 * zpool scrub [-s] <pool> ...
3787 *
3788 *	-s	Stop.  Stops any in-progress scrub.
3789 */
3790int
3791zpool_do_scrub(int argc, char **argv)
3792{
3793	int c;
3794	scrub_cbdata_t cb;
3795
3796	cb.cb_type = POOL_SCAN_SCRUB;
3797
3798	/* check options */
3799	while ((c = getopt(argc, argv, "s")) != -1) {
3800		switch (c) {
3801		case 's':
3802			cb.cb_type = POOL_SCAN_NONE;
3803			break;
3804		case '?':
3805			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
3806			    optopt);
3807			usage(B_FALSE);
3808		}
3809	}
3810
3811	cb.cb_argc = argc;
3812	cb.cb_argv = argv;
3813	argc -= optind;
3814	argv += optind;
3815
3816	if (argc < 1) {
3817		(void) fprintf(stderr, gettext("missing pool name argument\n"));
3818		usage(B_FALSE);
3819	}
3820
3821	return (for_each_pool(argc, argv, B_TRUE, NULL, scrub_callback, &cb));
3822}
3823
3824typedef struct status_cbdata {
3825	int		cb_count;
3826	boolean_t	cb_allpools;
3827	boolean_t	cb_verbose;
3828	boolean_t	cb_explain;
3829	boolean_t	cb_first;
3830	boolean_t	cb_dedup_stats;
3831} status_cbdata_t;
3832
3833/*
3834 * Print out detailed scrub status.
3835 */
3836void
3837print_scan_status(pool_scan_stat_t *ps)
3838{
3839	time_t start, end;
3840	uint64_t elapsed, mins_left, hours_left;
3841	uint64_t pass_exam, examined, total;
3842	uint_t rate;
3843	double fraction_done;
3844	char processed_buf[7], examined_buf[7], total_buf[7], rate_buf[7];
3845
3846	(void) printf(gettext("  scan: "));
3847
3848	/* If there's never been a scan, there's not much to say. */
3849	if (ps == NULL || ps->pss_func == POOL_SCAN_NONE ||
3850	    ps->pss_func >= POOL_SCAN_FUNCS) {
3851		(void) printf(gettext("none requested\n"));
3852		return;
3853	}
3854
3855	start = ps->pss_start_time;
3856	end = ps->pss_end_time;
3857	zfs_nicenum(ps->pss_processed, processed_buf, sizeof (processed_buf));
3858
3859	assert(ps->pss_func == POOL_SCAN_SCRUB ||
3860	    ps->pss_func == POOL_SCAN_RESILVER);
3861	/*
3862	 * Scan is finished or canceled.
3863	 */
3864	if (ps->pss_state == DSS_FINISHED) {
3865		uint64_t minutes_taken = (end - start) / 60;
3866		char *fmt;
3867
3868		if (ps->pss_func == POOL_SCAN_SCRUB) {
3869			fmt = gettext("scrub repaired %s in %lluh%um with "
3870			    "%llu errors on %s");
3871		} else if (ps->pss_func == POOL_SCAN_RESILVER) {
3872			fmt = gettext("resilvered %s in %lluh%um with "
3873			    "%llu errors on %s");
3874		}
3875		/* LINTED */
3876		(void) printf(fmt, processed_buf,
3877		    (u_longlong_t)(minutes_taken / 60),
3878		    (uint_t)(minutes_taken % 60),
3879		    (u_longlong_t)ps->pss_errors,
3880		    ctime((time_t *)&end));
3881		return;
3882	} else if (ps->pss_state == DSS_CANCELED) {
3883		if (ps->pss_func == POOL_SCAN_SCRUB) {
3884			(void) printf(gettext("scrub canceled on %s"),
3885			    ctime(&end));
3886		} else if (ps->pss_func == POOL_SCAN_RESILVER) {
3887			(void) printf(gettext("resilver canceled on %s"),
3888			    ctime(&end));
3889		}
3890		return;
3891	}
3892
3893	assert(ps->pss_state == DSS_SCANNING);
3894
3895	/*
3896	 * Scan is in progress.
3897	 */
3898	if (ps->pss_func == POOL_SCAN_SCRUB) {
3899		(void) printf(gettext("scrub in progress since %s"),
3900		    ctime(&start));
3901	} else if (ps->pss_func == POOL_SCAN_RESILVER) {
3902		(void) printf(gettext("resilver in progress since %s"),
3903		    ctime(&start));
3904	}
3905
3906	examined = ps->pss_examined ? ps->pss_examined : 1;
3907	total = ps->pss_to_examine;
3908	fraction_done = (double)examined / total;
3909
3910	/* elapsed time for this pass */
3911	elapsed = time(NULL) - ps->pss_pass_start;
3912	elapsed = elapsed ? elapsed : 1;
3913	pass_exam = ps->pss_pass_exam ? ps->pss_pass_exam : 1;
3914	rate = pass_exam / elapsed;
3915	rate = rate ? rate : 1;
3916	mins_left = ((total - examined) / rate) / 60;
3917	hours_left = mins_left / 60;
3918
3919	zfs_nicenum(examined, examined_buf, sizeof (examined_buf));
3920	zfs_nicenum(total, total_buf, sizeof (total_buf));
3921	zfs_nicenum(rate, rate_buf, sizeof (rate_buf));
3922
3923	/*
3924	 * do not print estimated time if hours_left is more than 30 days
3925	 */
3926	(void) printf(gettext("        %s scanned out of %s at %s/s"),
3927	    examined_buf, total_buf, rate_buf);
3928	if (hours_left < (30 * 24)) {
3929		(void) printf(gettext(", %lluh%um to go\n"),
3930		    (u_longlong_t)hours_left, (uint_t)(mins_left % 60));
3931	} else {
3932		(void) printf(gettext(
3933		    ", (scan is slow, no estimated time)\n"));
3934	}
3935
3936	if (ps->pss_func == POOL_SCAN_RESILVER) {
3937		(void) printf(gettext("        %s resilvered, %.2f%% done\n"),
3938		    processed_buf, 100 * fraction_done);
3939	} else if (ps->pss_func == POOL_SCAN_SCRUB) {
3940		(void) printf(gettext("        %s repaired, %.2f%% done\n"),
3941		    processed_buf, 100 * fraction_done);
3942	}
3943}
3944
3945static void
3946print_error_log(zpool_handle_t *zhp)
3947{
3948	nvlist_t *nverrlist = NULL;
3949	nvpair_t *elem;
3950	char *pathname;
3951	size_t len = MAXPATHLEN * 2;
3952
3953	if (zpool_get_errlog(zhp, &nverrlist) != 0) {
3954		(void) printf("errors: List of errors unavailable "
3955		    "(insufficient privileges)\n");
3956		return;
3957	}
3958
3959	(void) printf("errors: Permanent errors have been "
3960	    "detected in the following files:\n\n");
3961
3962	pathname = safe_malloc(len);
3963	elem = NULL;
3964	while ((elem = nvlist_next_nvpair(nverrlist, elem)) != NULL) {
3965		nvlist_t *nv;
3966		uint64_t dsobj, obj;
3967
3968		verify(nvpair_value_nvlist(elem, &nv) == 0);
3969		verify(nvlist_lookup_uint64(nv, ZPOOL_ERR_DATASET,
3970		    &dsobj) == 0);
3971		verify(nvlist_lookup_uint64(nv, ZPOOL_ERR_OBJECT,
3972		    &obj) == 0);
3973		zpool_obj_to_path(zhp, dsobj, obj, pathname, len);
3974		(void) printf("%7s %s\n", "", pathname);
3975	}
3976	free(pathname);
3977	nvlist_free(nverrlist);
3978}
3979
3980static void
3981print_spares(zpool_handle_t *zhp, nvlist_t **spares, uint_t nspares,
3982    int namewidth)
3983{
3984	uint_t i;
3985	char *name;
3986
3987	if (nspares == 0)
3988		return;
3989
3990	(void) printf(gettext("\tspares\n"));
3991
3992	for (i = 0; i < nspares; i++) {
3993		name = zpool_vdev_name(g_zfs, zhp, spares[i], B_FALSE);
3994		print_status_config(zhp, name, spares[i],
3995		    namewidth, 2, B_TRUE);
3996		free(name);
3997	}
3998}
3999
4000static void
4001print_l2cache(zpool_handle_t *zhp, nvlist_t **l2cache, uint_t nl2cache,
4002    int namewidth)
4003{
4004	uint_t i;
4005	char *name;
4006
4007	if (nl2cache == 0)
4008		return;
4009
4010	(void) printf(gettext("\tcache\n"));
4011
4012	for (i = 0; i < nl2cache; i++) {
4013		name = zpool_vdev_name(g_zfs, zhp, l2cache[i], B_FALSE);
4014		print_status_config(zhp, name, l2cache[i],
4015		    namewidth, 2, B_FALSE);
4016		free(name);
4017	}
4018}
4019
4020static void
4021print_dedup_stats(nvlist_t *config)
4022{
4023	ddt_histogram_t *ddh;
4024	ddt_stat_t *dds;
4025	ddt_object_t *ddo;
4026	uint_t c;
4027
4028	/*
4029	 * If the pool was faulted then we may not have been able to
4030	 * obtain the config. Otherwise, if have anything in the dedup
4031	 * table continue processing the stats.
4032	 */
4033	if (nvlist_lookup_uint64_array(config, ZPOOL_CONFIG_DDT_OBJ_STATS,
4034	    (uint64_t **)&ddo, &c) != 0)
4035		return;
4036
4037	(void) printf("\n");
4038	(void) printf(gettext(" dedup: "));
4039	if (ddo->ddo_count == 0) {
4040		(void) printf(gettext("no DDT entries\n"));
4041		return;
4042	}
4043
4044	(void) printf("DDT entries %llu, size %llu on disk, %llu in core\n",
4045	    (u_longlong_t)ddo->ddo_count,
4046	    (u_longlong_t)ddo->ddo_dspace,
4047	    (u_longlong_t)ddo->ddo_mspace);
4048
4049	verify(nvlist_lookup_uint64_array(config, ZPOOL_CONFIG_DDT_STATS,
4050	    (uint64_t **)&dds, &c) == 0);
4051	verify(nvlist_lookup_uint64_array(config, ZPOOL_CONFIG_DDT_HISTOGRAM,
4052	    (uint64_t **)&ddh, &c) == 0);
4053	zpool_dump_ddt(dds, ddh);
4054}
4055
4056/*
4057 * Display a summary of pool status.  Displays a summary such as:
4058 *
4059 *        pool: tank
4060 *	status: DEGRADED
4061 *	reason: One or more devices ...
4062 *         see: http://illumos.org/msg/ZFS-xxxx-01
4063 *	config:
4064 *		mirror		DEGRADED
4065 *                c1t0d0	OK
4066 *                c2t0d0	UNAVAIL
4067 *
4068 * When given the '-v' option, we print out the complete config.  If the '-e'
4069 * option is specified, then we print out error rate information as well.
4070 */
4071int
4072status_callback(zpool_handle_t *zhp, void *data)
4073{
4074	status_cbdata_t *cbp = data;
4075	nvlist_t *config, *nvroot;
4076	char *msgid;
4077	int reason;
4078	const char *health;
4079	uint_t c;
4080	vdev_stat_t *vs;
4081
4082	config = zpool_get_config(zhp, NULL);
4083	reason = zpool_get_status(zhp, &msgid);
4084
4085	cbp->cb_count++;
4086
4087	/*
4088	 * If we were given 'zpool status -x', only report those pools with
4089	 * problems.
4090	 */
4091	if (cbp->cb_explain &&
4092	    (reason == ZPOOL_STATUS_OK ||
4093	    reason == ZPOOL_STATUS_VERSION_OLDER ||
4094	    reason == ZPOOL_STATUS_FEAT_DISABLED)) {
4095		if (!cbp->cb_allpools) {
4096			(void) printf(gettext("pool '%s' is healthy\n"),
4097			    zpool_get_name(zhp));
4098			if (cbp->cb_first)
4099				cbp->cb_first = B_FALSE;
4100		}
4101		return (0);
4102	}
4103
4104	if (cbp->cb_first)
4105		cbp->cb_first = B_FALSE;
4106	else
4107		(void) printf("\n");
4108
4109	verify(nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE,
4110	    &nvroot) == 0);
4111	verify(nvlist_lookup_uint64_array(nvroot, ZPOOL_CONFIG_VDEV_STATS,
4112	    (uint64_t **)&vs, &c) == 0);
4113	health = zpool_state_to_name(vs->vs_state, vs->vs_aux);
4114
4115	(void) printf(gettext("  pool: %s\n"), zpool_get_name(zhp));
4116	(void) printf(gettext(" state: %s\n"), health);
4117
4118	switch (reason) {
4119	case ZPOOL_STATUS_MISSING_DEV_R:
4120		(void) printf(gettext("status: One or more devices could not "
4121		    "be opened.  Sufficient replicas exist for\n\tthe pool to "
4122		    "continue functioning in a degraded state.\n"));
4123		(void) printf(gettext("action: Attach the missing device and "
4124		    "online it using 'zpool online'.\n"));
4125		break;
4126
4127	case ZPOOL_STATUS_MISSING_DEV_NR:
4128		(void) printf(gettext("status: One or more devices could not "
4129		    "be opened.  There are insufficient\n\treplicas for the "
4130		    "pool to continue functioning.\n"));
4131		(void) printf(gettext("action: Attach the missing device and "
4132		    "online it using 'zpool online'.\n"));
4133		break;
4134
4135	case ZPOOL_STATUS_CORRUPT_LABEL_R:
4136		(void) printf(gettext("status: One or more devices could not "
4137		    "be used because the label is missing or\n\tinvalid.  "
4138		    "Sufficient replicas exist for the pool to continue\n\t"
4139		    "functioning in a degraded state.\n"));
4140		(void) printf(gettext("action: Replace the device using "
4141		    "'zpool replace'.\n"));
4142		break;
4143
4144	case ZPOOL_STATUS_CORRUPT_LABEL_NR:
4145		(void) printf(gettext("status: One or more devices could not "
4146		    "be used because the label is missing \n\tor invalid.  "
4147		    "There are insufficient replicas for the pool to "
4148		    "continue\n\tfunctioning.\n"));
4149		zpool_explain_recover(zpool_get_handle(zhp),
4150		    zpool_get_name(zhp), reason, config);
4151		break;
4152
4153	case ZPOOL_STATUS_FAILING_DEV:
4154		(void) printf(gettext("status: One or more devices has "
4155		    "experienced an unrecoverable error.  An\n\tattempt was "
4156		    "made to correct the error.  Applications are "
4157		    "unaffected.\n"));
4158		(void) printf(gettext("action: Determine if the device needs "
4159		    "to be replaced, and clear the errors\n\tusing "
4160		    "'zpool clear' or replace the device with 'zpool "
4161		    "replace'.\n"));
4162		break;
4163
4164	case ZPOOL_STATUS_OFFLINE_DEV:
4165		(void) printf(gettext("status: One or more devices has "
4166		    "been taken offline by the administrator.\n\tSufficient "
4167		    "replicas exist for the pool to continue functioning in "
4168		    "a\n\tdegraded state.\n"));
4169		(void) printf(gettext("action: Online the device using "
4170		    "'zpool online' or replace the device with\n\t'zpool "
4171		    "replace'.\n"));
4172		break;
4173
4174	case ZPOOL_STATUS_REMOVED_DEV:
4175		(void) printf(gettext("status: One or more devices has "
4176		    "been removed by the administrator.\n\tSufficient "
4177		    "replicas exist for the pool to continue functioning in "
4178		    "a\n\tdegraded state.\n"));
4179		(void) printf(gettext("action: Online the device using "
4180		    "'zpool online' or replace the device with\n\t'zpool "
4181		    "replace'.\n"));
4182		break;
4183
4184	case ZPOOL_STATUS_RESILVERING:
4185		(void) printf(gettext("status: One or more devices is "
4186		    "currently being resilvered.  The pool will\n\tcontinue "
4187		    "to function, possibly in a degraded state.\n"));
4188		(void) printf(gettext("action: Wait for the resilver to "
4189		    "complete.\n"));
4190		break;
4191
4192	case ZPOOL_STATUS_CORRUPT_DATA:
4193		(void) printf(gettext("status: One or more devices has "
4194		    "experienced an error resulting in data\n\tcorruption.  "
4195		    "Applications may be affected.\n"));
4196		(void) printf(gettext("action: Restore the file in question "
4197		    "if possible.  Otherwise restore the\n\tentire pool from "
4198		    "backup.\n"));
4199		break;
4200
4201	case ZPOOL_STATUS_CORRUPT_POOL:
4202		(void) printf(gettext("status: The pool metadata is corrupted "
4203		    "and the pool cannot be opened.\n"));
4204		zpool_explain_recover(zpool_get_handle(zhp),
4205		    zpool_get_name(zhp), reason, config);
4206		break;
4207
4208	case ZPOOL_STATUS_VERSION_OLDER:
4209		(void) printf(gettext("status: The pool is formatted using a "
4210		    "legacy on-disk format.  The pool can\n\tstill be used, "
4211		    "but some features are unavailable.\n"));
4212		(void) printf(gettext("action: Upgrade the pool using 'zpool "
4213		    "upgrade'.  Once this is done, the\n\tpool will no longer "
4214		    "be accessible on software that does not support feature\n"
4215		    "\tflags.\n"));
4216		break;
4217
4218	case ZPOOL_STATUS_VERSION_NEWER:
4219		(void) printf(gettext("status: The pool has been upgraded to a "
4220		    "newer, incompatible on-disk version.\n\tThe pool cannot "
4221		    "be accessed on this system.\n"));
4222		(void) printf(gettext("action: Access the pool from a system "
4223		    "running more recent software, or\n\trestore the pool from "
4224		    "backup.\n"));
4225		break;
4226
4227	case ZPOOL_STATUS_FEAT_DISABLED:
4228		(void) printf(gettext("status: Some supported features are not "
4229		    "enabled on the pool. The pool can\n\tstill be used, but "
4230		    "some features are unavailable.\n"));
4231		(void) printf(gettext("action: Enable all features using "
4232		    "'zpool upgrade'. Once this is done,\n\tthe pool may no "
4233		    "longer be accessible by software that does not support\n\t"
4234		    "the features. See zpool-features(7) for details.\n"));
4235		break;
4236
4237	case ZPOOL_STATUS_UNSUP_FEAT_READ:
4238		(void) printf(gettext("status: The pool cannot be accessed on "
4239		    "this system because it uses the\n\tfollowing feature(s) "
4240		    "not supported on this system:\n"));
4241		zpool_print_unsup_feat(config);
4242		(void) printf("\n");
4243		(void) printf(gettext("action: Access the pool from a system "
4244		    "that supports the required feature(s),\n\tor restore the "
4245		    "pool from backup.\n"));
4246		break;
4247
4248	case ZPOOL_STATUS_UNSUP_FEAT_WRITE:
4249		(void) printf(gettext("status: The pool can only be accessed "
4250		    "in read-only mode on this system. It\n\tcannot be "
4251		    "accessed in read-write mode because it uses the "
4252		    "following\n\tfeature(s) not supported on this system:\n"));
4253		zpool_print_unsup_feat(config);
4254		(void) printf("\n");
4255		(void) printf(gettext("action: The pool cannot be accessed in "
4256		    "read-write mode. Import the pool with\n"
4257		    "\t\"-o readonly=on\", access the pool from a system that "
4258		    "supports the\n\trequired feature(s), or restore the "
4259		    "pool from backup.\n"));
4260		break;
4261
4262	case ZPOOL_STATUS_FAULTED_DEV_R:
4263		(void) printf(gettext("status: One or more devices are "
4264		    "faulted in response to persistent errors.\n\tSufficient "
4265		    "replicas exist for the pool to continue functioning "
4266		    "in a\n\tdegraded state.\n"));
4267		(void) printf(gettext("action: Replace the faulted device, "
4268		    "or use 'zpool clear' to mark the device\n\trepaired.\n"));
4269		break;
4270
4271	case ZPOOL_STATUS_FAULTED_DEV_NR:
4272		(void) printf(gettext("status: One or more devices are "
4273		    "faulted in response to persistent errors.  There are "
4274		    "insufficient replicas for the pool to\n\tcontinue "
4275		    "functioning.\n"));
4276		(void) printf(gettext("action: Destroy and re-create the pool "
4277		    "from a backup source.  Manually marking the device\n"
4278		    "\trepaired using 'zpool clear' may allow some data "
4279		    "to be recovered.\n"));
4280		break;
4281
4282	case ZPOOL_STATUS_IO_FAILURE_WAIT:
4283	case ZPOOL_STATUS_IO_FAILURE_CONTINUE:
4284		(void) printf(gettext("status: One or more devices are "
4285		    "faulted in response to IO failures.\n"));
4286		(void) printf(gettext("action: Make sure the affected devices "
4287		    "are connected, then run 'zpool clear'.\n"));
4288		break;
4289
4290	case ZPOOL_STATUS_BAD_LOG:
4291		(void) printf(gettext("status: An intent log record "
4292		    "could not be read.\n"
4293		    "\tWaiting for adminstrator intervention to fix the "
4294		    "faulted pool.\n"));
4295		(void) printf(gettext("action: Either restore the affected "
4296		    "device(s) and run 'zpool online',\n"
4297		    "\tor ignore the intent log records by running "
4298		    "'zpool clear'.\n"));
4299		break;
4300
4301	case ZPOOL_STATUS_NON_NATIVE_ASHIFT:
4302		(void) printf(gettext("status: One or more devices are "
4303		    "configured to use a non-native block size.\n"
4304		    "\tExpect reduced performance.\n"));
4305		(void) printf(gettext("action: Replace affected devices with "
4306		    "devices that support the\n\tconfigured block size, or "
4307		    "migrate data to a properly configured\n\tpool.\n"));
4308		break;
4309
4310	default:
4311		/*
4312		 * The remaining errors can't actually be generated, yet.
4313		 */
4314		assert(reason == ZPOOL_STATUS_OK);
4315	}
4316
4317	if (msgid != NULL)
4318		(void) printf(gettext("   see: http://illumos.org/msg/%s\n"),
4319		    msgid);
4320
4321	if (config != NULL) {
4322		int namewidth;
4323		uint64_t nerr;
4324		nvlist_t **spares, **l2cache;
4325		uint_t nspares, nl2cache;
4326		pool_scan_stat_t *ps = NULL;
4327
4328		(void) nvlist_lookup_uint64_array(nvroot,
4329		    ZPOOL_CONFIG_SCAN_STATS, (uint64_t **)&ps, &c);
4330		print_scan_status(ps);
4331
4332		namewidth = max_width(zhp, nvroot, 0, 0);
4333		if (namewidth < 10)
4334			namewidth = 10;
4335
4336		(void) printf(gettext("config:\n\n"));
4337		(void) printf(gettext("\t%-*s  %-8s %5s %5s %5s\n"), namewidth,
4338		    "NAME", "STATE", "READ", "WRITE", "CKSUM");
4339		print_status_config(zhp, zpool_get_name(zhp), nvroot,
4340		    namewidth, 0, B_FALSE);
4341
4342		if (num_logs(nvroot) > 0)
4343			print_logs(zhp, nvroot, namewidth, B_TRUE);
4344		if (nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_L2CACHE,
4345		    &l2cache, &nl2cache) == 0)
4346			print_l2cache(zhp, l2cache, nl2cache, namewidth);
4347
4348		if (nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_SPARES,
4349		    &spares, &nspares) == 0)
4350			print_spares(zhp, spares, nspares, namewidth);
4351
4352		if (nvlist_lookup_uint64(config, ZPOOL_CONFIG_ERRCOUNT,
4353		    &nerr) == 0) {
4354			nvlist_t *nverrlist = NULL;
4355
4356			/*
4357			 * If the approximate error count is small, get a
4358			 * precise count by fetching the entire log and
4359			 * uniquifying the results.
4360			 */
4361			if (nerr > 0 && nerr < 100 && !cbp->cb_verbose &&
4362			    zpool_get_errlog(zhp, &nverrlist) == 0) {
4363				nvpair_t *elem;
4364
4365				elem = NULL;
4366				nerr = 0;
4367				while ((elem = nvlist_next_nvpair(nverrlist,
4368				    elem)) != NULL) {
4369					nerr++;
4370				}
4371			}
4372			nvlist_free(nverrlist);
4373
4374			(void) printf("\n");
4375
4376			if (nerr == 0)
4377				(void) printf(gettext("errors: No known data "
4378				    "errors\n"));
4379			else if (!cbp->cb_verbose)
4380				(void) printf(gettext("errors: %llu data "
4381				    "errors, use '-v' for a list\n"),
4382				    (u_longlong_t)nerr);
4383			else
4384				print_error_log(zhp);
4385		}
4386
4387		if (cbp->cb_dedup_stats)
4388			print_dedup_stats(config);
4389	} else {
4390		(void) printf(gettext("config: The configuration cannot be "
4391		    "determined.\n"));
4392	}
4393
4394	return (0);
4395}
4396
4397/*
4398 * zpool status [-vx] [-T d|u] [pool] ... [interval [count]]
4399 *
4400 *	-v	Display complete error logs
4401 *	-x	Display only pools with potential problems
4402 *	-D	Display dedup status (undocumented)
4403 *	-T	Display a timestamp in date(1) or Unix format
4404 *
4405 * Describes the health status of all pools or some subset.
4406 */
4407int
4408zpool_do_status(int argc, char **argv)
4409{
4410	int c;
4411	int ret;
4412	unsigned long interval = 0, count = 0;
4413	status_cbdata_t cb = { 0 };
4414
4415	/* check options */
4416	while ((c = getopt(argc, argv, "vxDT:")) != -1) {
4417		switch (c) {
4418		case 'v':
4419			cb.cb_verbose = B_TRUE;
4420			break;
4421		case 'x':
4422			cb.cb_explain = B_TRUE;
4423			break;
4424		case 'D':
4425			cb.cb_dedup_stats = B_TRUE;
4426			break;
4427		case 'T':
4428			get_timestamp_arg(*optarg);
4429			break;
4430		case '?':
4431			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
4432			    optopt);
4433			usage(B_FALSE);
4434		}
4435	}
4436
4437	argc -= optind;
4438	argv += optind;
4439
4440	get_interval_count(&argc, argv, &interval, &count);
4441
4442	if (argc == 0)
4443		cb.cb_allpools = B_TRUE;
4444
4445	cb.cb_first = B_TRUE;
4446
4447	for (;;) {
4448		if (timestamp_fmt != NODATE)
4449			print_timestamp(timestamp_fmt);
4450
4451		ret = for_each_pool(argc, argv, B_TRUE, NULL,
4452		    status_callback, &cb);
4453
4454		if (argc == 0 && cb.cb_count == 0)
4455			(void) printf(gettext("no pools available\n"));
4456		else if (cb.cb_explain && cb.cb_first && cb.cb_allpools)
4457			(void) printf(gettext("all pools are healthy\n"));
4458
4459		if (ret != 0)
4460			return (ret);
4461
4462		if (interval == 0)
4463			break;
4464
4465		if (count != 0 && --count == 0)
4466			break;
4467
4468		(void) sleep(interval);
4469	}
4470
4471	return (0);
4472}
4473
4474typedef struct upgrade_cbdata {
4475	int	cb_first;
4476	char	cb_poolname[ZPOOL_MAXNAMELEN];
4477	int	cb_argc;
4478	uint64_t cb_version;
4479	char	**cb_argv;
4480} upgrade_cbdata_t;
4481
4482#ifdef __FreeBSD__
4483static int
4484is_root_pool(zpool_handle_t *zhp)
4485{
4486	static struct statfs sfs;
4487	static char *poolname = NULL;
4488	static boolean_t stated = B_FALSE;
4489	char *slash;
4490
4491	if (!stated) {
4492		stated = B_TRUE;
4493		if (statfs("/", &sfs) == -1) {
4494			(void) fprintf(stderr,
4495			    "Unable to stat root file system: %s.\n",
4496			    strerror(errno));
4497			return (0);
4498		}
4499		if (strcmp(sfs.f_fstypename, "zfs") != 0)
4500			return (0);
4501		poolname = sfs.f_mntfromname;
4502		if ((slash = strchr(poolname, '/')) != NULL)
4503			*slash = '\0';
4504	}
4505	return (poolname != NULL && strcmp(poolname, zpool_get_name(zhp)) == 0);
4506}
4507
4508static void
4509root_pool_upgrade_check(zpool_handle_t *zhp, char *poolname, int size) {
4510
4511	if (poolname[0] == '\0' && is_root_pool(zhp))
4512		(void) strlcpy(poolname, zpool_get_name(zhp), size);
4513}
4514#endif	/* FreeBSD */
4515
4516static int
4517upgrade_version(zpool_handle_t *zhp, uint64_t version)
4518{
4519	int ret;
4520	nvlist_t *config;
4521	uint64_t oldversion;
4522
4523	config = zpool_get_config(zhp, NULL);
4524	verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
4525	    &oldversion) == 0);
4526
4527	assert(SPA_VERSION_IS_SUPPORTED(oldversion));
4528	assert(oldversion < version);
4529
4530	ret = zpool_upgrade(zhp, version);
4531	if (ret != 0)
4532		return (ret);
4533
4534	if (version >= SPA_VERSION_FEATURES) {
4535		(void) printf(gettext("Successfully upgraded "
4536		    "'%s' from version %llu to feature flags.\n"),
4537		    zpool_get_name(zhp), oldversion);
4538	} else {
4539		(void) printf(gettext("Successfully upgraded "
4540		    "'%s' from version %llu to version %llu.\n"),
4541		    zpool_get_name(zhp), oldversion, version);
4542	}
4543
4544	return (0);
4545}
4546
4547static int
4548upgrade_enable_all(zpool_handle_t *zhp, int *countp)
4549{
4550	int i, ret, count;
4551	boolean_t firstff = B_TRUE;
4552	nvlist_t *enabled = zpool_get_features(zhp);
4553
4554	count = 0;
4555	for (i = 0; i < SPA_FEATURES; i++) {
4556		const char *fname = spa_feature_table[i].fi_uname;
4557		const char *fguid = spa_feature_table[i].fi_guid;
4558		if (!nvlist_exists(enabled, fguid)) {
4559			char *propname;
4560			verify(-1 != asprintf(&propname, "feature@%s", fname));
4561			ret = zpool_set_prop(zhp, propname,
4562			    ZFS_FEATURE_ENABLED);
4563			if (ret != 0) {
4564				free(propname);
4565				return (ret);
4566			}
4567			count++;
4568
4569			if (firstff) {
4570				(void) printf(gettext("Enabled the "
4571				    "following features on '%s':\n"),
4572				    zpool_get_name(zhp));
4573				firstff = B_FALSE;
4574			}
4575			(void) printf(gettext("  %s\n"), fname);
4576			free(propname);
4577		}
4578	}
4579
4580	if (countp != NULL)
4581		*countp = count;
4582	return (0);
4583}
4584
4585static int
4586upgrade_cb(zpool_handle_t *zhp, void *arg)
4587{
4588	upgrade_cbdata_t *cbp = arg;
4589	nvlist_t *config;
4590	uint64_t version;
4591	boolean_t printnl = B_FALSE;
4592	int ret;
4593
4594	config = zpool_get_config(zhp, NULL);
4595	verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
4596	    &version) == 0);
4597
4598	assert(SPA_VERSION_IS_SUPPORTED(version));
4599
4600	if (version < cbp->cb_version) {
4601		cbp->cb_first = B_FALSE;
4602		ret = upgrade_version(zhp, cbp->cb_version);
4603		if (ret != 0)
4604			return (ret);
4605#ifdef __FreeBSD__
4606		root_pool_upgrade_check(zhp, cbp->cb_poolname,
4607		    sizeof(cbp->cb_poolname));
4608#endif	/* ___FreeBSD__ */
4609		printnl = B_TRUE;
4610
4611#ifdef illumos
4612		/*
4613		 * If they did "zpool upgrade -a", then we could
4614		 * be doing ioctls to different pools.  We need
4615		 * to log this history once to each pool, and bypass
4616		 * the normal history logging that happens in main().
4617		 */
4618		(void) zpool_log_history(g_zfs, history_str);
4619		log_history = B_FALSE;
4620#endif
4621	}
4622
4623	if (cbp->cb_version >= SPA_VERSION_FEATURES) {
4624		int count;
4625		ret = upgrade_enable_all(zhp, &count);
4626		if (ret != 0)
4627			return (ret);
4628
4629		if (count > 0) {
4630			cbp->cb_first = B_FALSE;
4631			printnl = B_TRUE;
4632			/*
4633			 * If they did "zpool upgrade -a", then we could
4634			 * be doing ioctls to different pools.  We need
4635			 * to log this history once to each pool, and bypass
4636			 * the normal history logging that happens in main().
4637			 */
4638			(void) zpool_log_history(g_zfs, history_str);
4639			log_history = B_FALSE;
4640		}
4641	}
4642
4643	if (printnl) {
4644		(void) printf(gettext("\n"));
4645	}
4646
4647	return (0);
4648}
4649
4650static int
4651upgrade_list_older_cb(zpool_handle_t *zhp, void *arg)
4652{
4653	upgrade_cbdata_t *cbp = arg;
4654	nvlist_t *config;
4655	uint64_t version;
4656
4657	config = zpool_get_config(zhp, NULL);
4658	verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
4659	    &version) == 0);
4660
4661	assert(SPA_VERSION_IS_SUPPORTED(version));
4662
4663	if (version < SPA_VERSION_FEATURES) {
4664		if (cbp->cb_first) {
4665			(void) printf(gettext("The following pools are "
4666			    "formatted with legacy version numbers and can\n"
4667			    "be upgraded to use feature flags.  After "
4668			    "being upgraded, these pools\nwill no "
4669			    "longer be accessible by software that does not "
4670			    "support feature\nflags.\n\n"));
4671			(void) printf(gettext("VER  POOL\n"));
4672			(void) printf(gettext("---  ------------\n"));
4673			cbp->cb_first = B_FALSE;
4674		}
4675
4676		(void) printf("%2llu   %s\n", (u_longlong_t)version,
4677		    zpool_get_name(zhp));
4678	}
4679
4680	return (0);
4681}
4682
4683static int
4684upgrade_list_disabled_cb(zpool_handle_t *zhp, void *arg)
4685{
4686	upgrade_cbdata_t *cbp = arg;
4687	nvlist_t *config;
4688	uint64_t version;
4689
4690	config = zpool_get_config(zhp, NULL);
4691	verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
4692	    &version) == 0);
4693
4694	if (version >= SPA_VERSION_FEATURES) {
4695		int i;
4696		boolean_t poolfirst = B_TRUE;
4697		nvlist_t *enabled = zpool_get_features(zhp);
4698
4699		for (i = 0; i < SPA_FEATURES; i++) {
4700			const char *fguid = spa_feature_table[i].fi_guid;
4701			const char *fname = spa_feature_table[i].fi_uname;
4702			if (!nvlist_exists(enabled, fguid)) {
4703				if (cbp->cb_first) {
4704					(void) printf(gettext("\nSome "
4705					    "supported features are not "
4706					    "enabled on the following pools. "
4707					    "Once a\nfeature is enabled the "
4708					    "pool may become incompatible with "
4709					    "software\nthat does not support "
4710					    "the feature. See "
4711					    "zpool-features(7) for "
4712					    "details.\n\n"));
4713					(void) printf(gettext("POOL  "
4714					    "FEATURE\n"));
4715					(void) printf(gettext("------"
4716					    "---------\n"));
4717					cbp->cb_first = B_FALSE;
4718				}
4719
4720				if (poolfirst) {
4721					(void) printf(gettext("%s\n"),
4722					    zpool_get_name(zhp));
4723					poolfirst = B_FALSE;
4724				}
4725
4726				(void) printf(gettext("      %s\n"), fname);
4727			}
4728		}
4729	}
4730
4731	return (0);
4732}
4733
4734/* ARGSUSED */
4735static int
4736upgrade_one(zpool_handle_t *zhp, void *data)
4737{
4738	boolean_t printnl = B_FALSE;
4739	upgrade_cbdata_t *cbp = data;
4740	uint64_t cur_version;
4741	int ret;
4742
4743	if (strcmp("log", zpool_get_name(zhp)) == 0) {
4744		(void) printf(gettext("'log' is now a reserved word\n"
4745		    "Pool 'log' must be renamed using export and import"
4746		    " to upgrade.\n"));
4747		return (1);
4748	}
4749
4750	cur_version = zpool_get_prop_int(zhp, ZPOOL_PROP_VERSION, NULL);
4751	if (cur_version > cbp->cb_version) {
4752		(void) printf(gettext("Pool '%s' is already formatted "
4753		    "using more current version '%llu'.\n\n"),
4754		    zpool_get_name(zhp), cur_version);
4755		return (0);
4756	}
4757
4758	if (cbp->cb_version != SPA_VERSION && cur_version == cbp->cb_version) {
4759		(void) printf(gettext("Pool '%s' is already formatted "
4760		    "using version %llu.\n\n"), zpool_get_name(zhp),
4761		    cbp->cb_version);
4762		return (0);
4763	}
4764
4765	if (cur_version != cbp->cb_version) {
4766		printnl = B_TRUE;
4767		ret = upgrade_version(zhp, cbp->cb_version);
4768		if (ret != 0)
4769			return (ret);
4770#ifdef __FreeBSD__
4771		root_pool_upgrade_check(zhp, cbp->cb_poolname,
4772		    sizeof(cbp->cb_poolname));
4773#endif	/* ___FreeBSD__ */
4774	}
4775
4776	if (cbp->cb_version >= SPA_VERSION_FEATURES) {
4777		int count = 0;
4778		ret = upgrade_enable_all(zhp, &count);
4779		if (ret != 0)
4780			return (ret);
4781
4782		if (count != 0) {
4783			printnl = B_TRUE;
4784#ifdef __FreeBSD__
4785			root_pool_upgrade_check(zhp, cbp->cb_poolname,
4786			    sizeof(cbp->cb_poolname));
4787#endif	/* __FreeBSD __*/
4788		} else if (cur_version == SPA_VERSION) {
4789			(void) printf(gettext("Pool '%s' already has all "
4790			    "supported features enabled.\n"),
4791			    zpool_get_name(zhp));
4792		}
4793	}
4794
4795	if (printnl) {
4796		(void) printf(gettext("\n"));
4797	}
4798
4799	return (0);
4800}
4801
4802/*
4803 * zpool upgrade
4804 * zpool upgrade -v
4805 * zpool upgrade [-V version] <-a | pool ...>
4806 *
4807 * With no arguments, display downrev'd ZFS pool available for upgrade.
4808 * Individual pools can be upgraded by specifying the pool, and '-a' will
4809 * upgrade all pools.
4810 */
4811int
4812zpool_do_upgrade(int argc, char **argv)
4813{
4814	int c;
4815	upgrade_cbdata_t cb = { 0 };
4816	int ret = 0;
4817	boolean_t showversions = B_FALSE;
4818	boolean_t upgradeall = B_FALSE;
4819	char *end;
4820
4821
4822	/* check options */
4823	while ((c = getopt(argc, argv, ":avV:")) != -1) {
4824		switch (c) {
4825		case 'a':
4826			upgradeall = B_TRUE;
4827			break;
4828		case 'v':
4829			showversions = B_TRUE;
4830			break;
4831		case 'V':
4832			cb.cb_version = strtoll(optarg, &end, 10);
4833			if (*end != '\0' ||
4834			    !SPA_VERSION_IS_SUPPORTED(cb.cb_version)) {
4835				(void) fprintf(stderr,
4836				    gettext("invalid version '%s'\n"), optarg);
4837				usage(B_FALSE);
4838			}
4839			break;
4840		case ':':
4841			(void) fprintf(stderr, gettext("missing argument for "
4842			    "'%c' option\n"), optopt);
4843			usage(B_FALSE);
4844			break;
4845		case '?':
4846			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
4847			    optopt);
4848			usage(B_FALSE);
4849		}
4850	}
4851
4852	cb.cb_argc = argc;
4853	cb.cb_argv = argv;
4854	argc -= optind;
4855	argv += optind;
4856
4857	if (cb.cb_version == 0) {
4858		cb.cb_version = SPA_VERSION;
4859	} else if (!upgradeall && argc == 0) {
4860		(void) fprintf(stderr, gettext("-V option is "
4861		    "incompatible with other arguments\n"));
4862		usage(B_FALSE);
4863	}
4864
4865	if (showversions) {
4866		if (upgradeall || argc != 0) {
4867			(void) fprintf(stderr, gettext("-v option is "
4868			    "incompatible with other arguments\n"));
4869			usage(B_FALSE);
4870		}
4871	} else if (upgradeall) {
4872		if (argc != 0) {
4873			(void) fprintf(stderr, gettext("-a option should not "
4874			    "be used along with a pool name\n"));
4875			usage(B_FALSE);
4876		}
4877	}
4878
4879	(void) printf(gettext("This system supports ZFS pool feature "
4880	    "flags.\n\n"));
4881	if (showversions) {
4882		int i;
4883
4884		(void) printf(gettext("The following features are "
4885		    "supported:\n\n"));
4886		(void) printf(gettext("FEAT DESCRIPTION\n"));
4887		(void) printf("----------------------------------------------"
4888		    "---------------\n");
4889		for (i = 0; i < SPA_FEATURES; i++) {
4890			zfeature_info_t *fi = &spa_feature_table[i];
4891			const char *ro = fi->fi_can_readonly ?
4892			    " (read-only compatible)" : "";
4893
4894			(void) printf("%-37s%s\n", fi->fi_uname, ro);
4895			(void) printf("     %s\n", fi->fi_desc);
4896		}
4897		(void) printf("\n");
4898
4899		(void) printf(gettext("The following legacy versions are also "
4900		    "supported:\n\n"));
4901		(void) printf(gettext("VER  DESCRIPTION\n"));
4902		(void) printf("---  -----------------------------------------"
4903		    "---------------\n");
4904		(void) printf(gettext(" 1   Initial ZFS version\n"));
4905		(void) printf(gettext(" 2   Ditto blocks "
4906		    "(replicated metadata)\n"));
4907		(void) printf(gettext(" 3   Hot spares and double parity "
4908		    "RAID-Z\n"));
4909		(void) printf(gettext(" 4   zpool history\n"));
4910		(void) printf(gettext(" 5   Compression using the gzip "
4911		    "algorithm\n"));
4912		(void) printf(gettext(" 6   bootfs pool property\n"));
4913		(void) printf(gettext(" 7   Separate intent log devices\n"));
4914		(void) printf(gettext(" 8   Delegated administration\n"));
4915		(void) printf(gettext(" 9   refquota and refreservation "
4916		    "properties\n"));
4917		(void) printf(gettext(" 10  Cache devices\n"));
4918		(void) printf(gettext(" 11  Improved scrub performance\n"));
4919		(void) printf(gettext(" 12  Snapshot properties\n"));
4920		(void) printf(gettext(" 13  snapused property\n"));
4921		(void) printf(gettext(" 14  passthrough-x aclinherit\n"));
4922		(void) printf(gettext(" 15  user/group space accounting\n"));
4923		(void) printf(gettext(" 16  stmf property support\n"));
4924		(void) printf(gettext(" 17  Triple-parity RAID-Z\n"));
4925		(void) printf(gettext(" 18  Snapshot user holds\n"));
4926		(void) printf(gettext(" 19  Log device removal\n"));
4927		(void) printf(gettext(" 20  Compression using zle "
4928		    "(zero-length encoding)\n"));
4929		(void) printf(gettext(" 21  Deduplication\n"));
4930		(void) printf(gettext(" 22  Received properties\n"));
4931		(void) printf(gettext(" 23  Slim ZIL\n"));
4932		(void) printf(gettext(" 24  System attributes\n"));
4933		(void) printf(gettext(" 25  Improved scrub stats\n"));
4934		(void) printf(gettext(" 26  Improved snapshot deletion "
4935		    "performance\n"));
4936		(void) printf(gettext(" 27  Improved snapshot creation "
4937		    "performance\n"));
4938		(void) printf(gettext(" 28  Multiple vdev replacements\n"));
4939		(void) printf(gettext("\nFor more information on a particular "
4940		    "version, including supported releases,\n"));
4941		(void) printf(gettext("see the ZFS Administration Guide.\n\n"));
4942	} else if (argc == 0 && upgradeall) {
4943		cb.cb_first = B_TRUE;
4944		ret = zpool_iter(g_zfs, upgrade_cb, &cb);
4945		if (ret == 0 && cb.cb_first) {
4946			if (cb.cb_version == SPA_VERSION) {
4947				(void) printf(gettext("All pools are already "
4948				    "formatted using feature flags.\n\n"));
4949				(void) printf(gettext("Every feature flags "
4950				    "pool already has all supported features "
4951				    "enabled.\n"));
4952			} else {
4953				(void) printf(gettext("All pools are already "
4954				    "formatted with version %llu or higher.\n"),
4955				    cb.cb_version);
4956			}
4957		}
4958	} else if (argc == 0) {
4959		cb.cb_first = B_TRUE;
4960		ret = zpool_iter(g_zfs, upgrade_list_older_cb, &cb);
4961		assert(ret == 0);
4962
4963		if (cb.cb_first) {
4964			(void) printf(gettext("All pools are formatted "
4965			    "using feature flags.\n\n"));
4966		} else {
4967			(void) printf(gettext("\nUse 'zpool upgrade -v' "
4968			    "for a list of available legacy versions.\n"));
4969		}
4970
4971		cb.cb_first = B_TRUE;
4972		ret = zpool_iter(g_zfs, upgrade_list_disabled_cb, &cb);
4973		assert(ret == 0);
4974
4975		if (cb.cb_first) {
4976			(void) printf(gettext("Every feature flags pool has "
4977			    "all supported features enabled.\n"));
4978		} else {
4979			(void) printf(gettext("\n"));
4980		}
4981	} else {
4982		ret = for_each_pool(argc, argv, B_FALSE, NULL,
4983		    upgrade_one, &cb);
4984	}
4985
4986	if (cb.cb_poolname[0] != '\0') {
4987		(void) printf(
4988		    "If you boot from pool '%s', don't forget to update boot code.\n"
4989		    "Assuming you use GPT partitioning and da0 is your boot disk\n"
4990		    "the following command will do it:\n"
4991		    "\n"
4992		    "\tgpart bootcode -b /boot/pmbr -p /boot/gptzfsboot -i 1 da0\n\n",
4993		    cb.cb_poolname);
4994	}
4995
4996	return (ret);
4997}
4998
4999typedef struct hist_cbdata {
5000	boolean_t first;
5001	boolean_t longfmt;
5002	boolean_t internal;
5003} hist_cbdata_t;
5004
5005/*
5006 * Print out the command history for a specific pool.
5007 */
5008static int
5009get_history_one(zpool_handle_t *zhp, void *data)
5010{
5011	nvlist_t *nvhis;
5012	nvlist_t **records;
5013	uint_t numrecords;
5014	int ret, i;
5015	hist_cbdata_t *cb = (hist_cbdata_t *)data;
5016
5017	cb->first = B_FALSE;
5018
5019	(void) printf(gettext("History for '%s':\n"), zpool_get_name(zhp));
5020
5021	if ((ret = zpool_get_history(zhp, &nvhis)) != 0)
5022		return (ret);
5023
5024	verify(nvlist_lookup_nvlist_array(nvhis, ZPOOL_HIST_RECORD,
5025	    &records, &numrecords) == 0);
5026	for (i = 0; i < numrecords; i++) {
5027		nvlist_t *rec = records[i];
5028		char tbuf[30] = "";
5029
5030		if (nvlist_exists(rec, ZPOOL_HIST_TIME)) {
5031			time_t tsec;
5032			struct tm t;
5033
5034			tsec = fnvlist_lookup_uint64(records[i],
5035			    ZPOOL_HIST_TIME);
5036			(void) localtime_r(&tsec, &t);
5037			(void) strftime(tbuf, sizeof (tbuf), "%F.%T", &t);
5038		}
5039
5040		if (nvlist_exists(rec, ZPOOL_HIST_CMD)) {
5041			(void) printf("%s %s", tbuf,
5042			    fnvlist_lookup_string(rec, ZPOOL_HIST_CMD));
5043		} else if (nvlist_exists(rec, ZPOOL_HIST_INT_EVENT)) {
5044			int ievent =
5045			    fnvlist_lookup_uint64(rec, ZPOOL_HIST_INT_EVENT);
5046			if (!cb->internal)
5047				continue;
5048			if (ievent >= ZFS_NUM_LEGACY_HISTORY_EVENTS) {
5049				(void) printf("%s unrecognized record:\n",
5050				    tbuf);
5051				dump_nvlist(rec, 4);
5052				continue;
5053			}
5054			(void) printf("%s [internal %s txg:%lld] %s", tbuf,
5055			    zfs_history_event_names[ievent],
5056			    fnvlist_lookup_uint64(rec, ZPOOL_HIST_TXG),
5057			    fnvlist_lookup_string(rec, ZPOOL_HIST_INT_STR));
5058		} else if (nvlist_exists(rec, ZPOOL_HIST_INT_NAME)) {
5059			if (!cb->internal)
5060				continue;
5061			(void) printf("%s [txg:%lld] %s", tbuf,
5062			    fnvlist_lookup_uint64(rec, ZPOOL_HIST_TXG),
5063			    fnvlist_lookup_string(rec, ZPOOL_HIST_INT_NAME));
5064			if (nvlist_exists(rec, ZPOOL_HIST_DSNAME)) {
5065				(void) printf(" %s (%llu)",
5066				    fnvlist_lookup_string(rec,
5067				    ZPOOL_HIST_DSNAME),
5068				    fnvlist_lookup_uint64(rec,
5069				    ZPOOL_HIST_DSID));
5070			}
5071			(void) printf(" %s", fnvlist_lookup_string(rec,
5072			    ZPOOL_HIST_INT_STR));
5073		} else if (nvlist_exists(rec, ZPOOL_HIST_IOCTL)) {
5074			if (!cb->internal)
5075				continue;
5076			(void) printf("%s ioctl %s\n", tbuf,
5077			    fnvlist_lookup_string(rec, ZPOOL_HIST_IOCTL));
5078			if (nvlist_exists(rec, ZPOOL_HIST_INPUT_NVL)) {
5079				(void) printf("    input:\n");
5080				dump_nvlist(fnvlist_lookup_nvlist(rec,
5081				    ZPOOL_HIST_INPUT_NVL), 8);
5082			}
5083			if (nvlist_exists(rec, ZPOOL_HIST_OUTPUT_NVL)) {
5084				(void) printf("    output:\n");
5085				dump_nvlist(fnvlist_lookup_nvlist(rec,
5086				    ZPOOL_HIST_OUTPUT_NVL), 8);
5087			}
5088		} else {
5089			if (!cb->internal)
5090				continue;
5091			(void) printf("%s unrecognized record:\n", tbuf);
5092			dump_nvlist(rec, 4);
5093		}
5094
5095		if (!cb->longfmt) {
5096			(void) printf("\n");
5097			continue;
5098		}
5099		(void) printf(" [");
5100		if (nvlist_exists(rec, ZPOOL_HIST_WHO)) {
5101			uid_t who = fnvlist_lookup_uint64(rec, ZPOOL_HIST_WHO);
5102			struct passwd *pwd = getpwuid(who);
5103			(void) printf("user %d ", (int)who);
5104			if (pwd != NULL)
5105				(void) printf("(%s) ", pwd->pw_name);
5106		}
5107		if (nvlist_exists(rec, ZPOOL_HIST_HOST)) {
5108			(void) printf("on %s",
5109			    fnvlist_lookup_string(rec, ZPOOL_HIST_HOST));
5110		}
5111		if (nvlist_exists(rec, ZPOOL_HIST_ZONE)) {
5112			(void) printf(":%s",
5113			    fnvlist_lookup_string(rec, ZPOOL_HIST_ZONE));
5114		}
5115		(void) printf("]");
5116		(void) printf("\n");
5117	}
5118	(void) printf("\n");
5119	nvlist_free(nvhis);
5120
5121	return (ret);
5122}
5123
5124/*
5125 * zpool history <pool>
5126 *
5127 * Displays the history of commands that modified pools.
5128 */
5129int
5130zpool_do_history(int argc, char **argv)
5131{
5132	hist_cbdata_t cbdata = { 0 };
5133	int ret;
5134	int c;
5135
5136	cbdata.first = B_TRUE;
5137	/* check options */
5138	while ((c = getopt(argc, argv, "li")) != -1) {
5139		switch (c) {
5140		case 'l':
5141			cbdata.longfmt = B_TRUE;
5142			break;
5143		case 'i':
5144			cbdata.internal = B_TRUE;
5145			break;
5146		case '?':
5147			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
5148			    optopt);
5149			usage(B_FALSE);
5150		}
5151	}
5152	argc -= optind;
5153	argv += optind;
5154
5155	ret = for_each_pool(argc, argv, B_FALSE,  NULL, get_history_one,
5156	    &cbdata);
5157
5158	if (argc == 0 && cbdata.first == B_TRUE) {
5159		(void) printf(gettext("no pools available\n"));
5160		return (0);
5161	}
5162
5163	return (ret);
5164}
5165
5166static int
5167get_callback(zpool_handle_t *zhp, void *data)
5168{
5169	zprop_get_cbdata_t *cbp = (zprop_get_cbdata_t *)data;
5170	char value[MAXNAMELEN];
5171	zprop_source_t srctype;
5172	zprop_list_t *pl;
5173
5174	for (pl = cbp->cb_proplist; pl != NULL; pl = pl->pl_next) {
5175
5176		/*
5177		 * Skip the special fake placeholder. This will also skip
5178		 * over the name property when 'all' is specified.
5179		 */
5180		if (pl->pl_prop == ZPOOL_PROP_NAME &&
5181		    pl == cbp->cb_proplist)
5182			continue;
5183
5184		if (pl->pl_prop == ZPROP_INVAL &&
5185		    (zpool_prop_feature(pl->pl_user_prop) ||
5186		    zpool_prop_unsupported(pl->pl_user_prop))) {
5187			srctype = ZPROP_SRC_LOCAL;
5188
5189			if (zpool_prop_get_feature(zhp, pl->pl_user_prop,
5190			    value, sizeof (value)) == 0) {
5191				zprop_print_one_property(zpool_get_name(zhp),
5192				    cbp, pl->pl_user_prop, value, srctype,
5193				    NULL, NULL);
5194			}
5195		} else {
5196			if (zpool_get_prop(zhp, pl->pl_prop, value,
5197			    sizeof (value), &srctype, cbp->cb_literal) != 0)
5198				continue;
5199
5200			zprop_print_one_property(zpool_get_name(zhp), cbp,
5201			    zpool_prop_to_name(pl->pl_prop), value, srctype,
5202			    NULL, NULL);
5203		}
5204	}
5205	return (0);
5206}
5207
5208/*
5209 * zpool get [-Hp] [-o "all" | field[,...]] <"all" | property[,...]> <pool> ...
5210 *
5211 *	-H	Scripted mode.  Don't display headers, and separate properties
5212 *		by a single tab.
5213 *	-o	List of columns to display.  Defaults to
5214 *		"name,property,value,source".
5215 * 	-p	Diplay values in parsable (exact) format.
5216 *
5217 * Get properties of pools in the system. Output space statistics
5218 * for each one as well as other attributes.
5219 */
5220int
5221zpool_do_get(int argc, char **argv)
5222{
5223	zprop_get_cbdata_t cb = { 0 };
5224	zprop_list_t fake_name = { 0 };
5225	int ret;
5226	int c, i;
5227	char *value;
5228
5229	cb.cb_first = B_TRUE;
5230
5231	/*
5232	 * Set up default columns and sources.
5233	 */
5234	cb.cb_sources = ZPROP_SRC_ALL;
5235	cb.cb_columns[0] = GET_COL_NAME;
5236	cb.cb_columns[1] = GET_COL_PROPERTY;
5237	cb.cb_columns[2] = GET_COL_VALUE;
5238	cb.cb_columns[3] = GET_COL_SOURCE;
5239	cb.cb_type = ZFS_TYPE_POOL;
5240
5241	/* check options */
5242	while ((c = getopt(argc, argv, ":Hpo:")) != -1) {
5243		switch (c) {
5244		case 'p':
5245			cb.cb_literal = B_TRUE;
5246			break;
5247		case 'H':
5248			cb.cb_scripted = B_TRUE;
5249			break;
5250		case 'o':
5251			bzero(&cb.cb_columns, sizeof (cb.cb_columns));
5252			i = 0;
5253			while (*optarg != '\0') {
5254				static char *col_subopts[] =
5255				{ "name", "property", "value", "source",
5256				"all", NULL };
5257
5258				if (i == ZFS_GET_NCOLS) {
5259					(void) fprintf(stderr, gettext("too "
5260					"many fields given to -o "
5261					"option\n"));
5262					usage(B_FALSE);
5263				}
5264
5265				switch (getsubopt(&optarg, col_subopts,
5266				    &value)) {
5267				case 0:
5268					cb.cb_columns[i++] = GET_COL_NAME;
5269					break;
5270				case 1:
5271					cb.cb_columns[i++] = GET_COL_PROPERTY;
5272					break;
5273				case 2:
5274					cb.cb_columns[i++] = GET_COL_VALUE;
5275					break;
5276				case 3:
5277					cb.cb_columns[i++] = GET_COL_SOURCE;
5278					break;
5279				case 4:
5280					if (i > 0) {
5281						(void) fprintf(stderr,
5282						    gettext("\"all\" conflicts "
5283						    "with specific fields "
5284						    "given to -o option\n"));
5285						usage(B_FALSE);
5286					}
5287					cb.cb_columns[0] = GET_COL_NAME;
5288					cb.cb_columns[1] = GET_COL_PROPERTY;
5289					cb.cb_columns[2] = GET_COL_VALUE;
5290					cb.cb_columns[3] = GET_COL_SOURCE;
5291					i = ZFS_GET_NCOLS;
5292					break;
5293				default:
5294					(void) fprintf(stderr,
5295					    gettext("invalid column name "
5296					    "'%s'\n"), value);
5297					usage(B_FALSE);
5298				}
5299			}
5300			break;
5301		case '?':
5302			(void) fprintf(stderr, gettext("invalid option '%c'\n"),
5303			    optopt);
5304			usage(B_FALSE);
5305		}
5306	}
5307
5308	argc -= optind;
5309	argv += optind;
5310
5311	if (argc < 1) {
5312		(void) fprintf(stderr, gettext("missing property "
5313		    "argument\n"));
5314		usage(B_FALSE);
5315	}
5316
5317	if (zprop_get_list(g_zfs, argv[0], &cb.cb_proplist,
5318	    ZFS_TYPE_POOL) != 0)
5319		usage(B_FALSE);
5320
5321	argc--;
5322	argv++;
5323
5324	if (cb.cb_proplist != NULL) {
5325		fake_name.pl_prop = ZPOOL_PROP_NAME;
5326		fake_name.pl_width = strlen(gettext("NAME"));
5327		fake_name.pl_next = cb.cb_proplist;
5328		cb.cb_proplist = &fake_name;
5329	}
5330
5331	ret = for_each_pool(argc, argv, B_TRUE, &cb.cb_proplist,
5332	    get_callback, &cb);
5333
5334	if (cb.cb_proplist == &fake_name)
5335		zprop_free_list(fake_name.pl_next);
5336	else
5337		zprop_free_list(cb.cb_proplist);
5338
5339	return (ret);
5340}
5341
5342typedef struct set_cbdata {
5343	char *cb_propname;
5344	char *cb_value;
5345	boolean_t cb_any_successful;
5346} set_cbdata_t;
5347
5348int
5349set_callback(zpool_handle_t *zhp, void *data)
5350{
5351	int error;
5352	set_cbdata_t *cb = (set_cbdata_t *)data;
5353
5354	error = zpool_set_prop(zhp, cb->cb_propname, cb->cb_value);
5355
5356	if (!error)
5357		cb->cb_any_successful = B_TRUE;
5358
5359	return (error);
5360}
5361
5362int
5363zpool_do_set(int argc, char **argv)
5364{
5365	set_cbdata_t cb = { 0 };
5366	int error;
5367
5368	if (argc > 1 && argv[1][0] == '-') {
5369		(void) fprintf(stderr, gettext("invalid option '%c'\n"),
5370		    argv[1][1]);
5371		usage(B_FALSE);
5372	}
5373
5374	if (argc < 2) {
5375		(void) fprintf(stderr, gettext("missing property=value "
5376		    "argument\n"));
5377		usage(B_FALSE);
5378	}
5379
5380	if (argc < 3) {
5381		(void) fprintf(stderr, gettext("missing pool name\n"));
5382		usage(B_FALSE);
5383	}
5384
5385	if (argc > 3) {
5386		(void) fprintf(stderr, gettext("too many pool names\n"));
5387		usage(B_FALSE);
5388	}
5389
5390	cb.cb_propname = argv[1];
5391	cb.cb_value = strchr(cb.cb_propname, '=');
5392	if (cb.cb_value == NULL) {
5393		(void) fprintf(stderr, gettext("missing value in "
5394		    "property=value argument\n"));
5395		usage(B_FALSE);
5396	}
5397
5398	*(cb.cb_value) = '\0';
5399	cb.cb_value++;
5400
5401	error = for_each_pool(argc - 2, argv + 2, B_TRUE, NULL,
5402	    set_callback, &cb);
5403
5404	return (error);
5405}
5406
5407static int
5408find_command_idx(char *command, int *idx)
5409{
5410	int i;
5411
5412	for (i = 0; i < NCOMMAND; i++) {
5413		if (command_table[i].name == NULL)
5414			continue;
5415
5416		if (strcmp(command, command_table[i].name) == 0) {
5417			*idx = i;
5418			return (0);
5419		}
5420	}
5421	return (1);
5422}
5423
5424int
5425main(int argc, char **argv)
5426{
5427	int ret;
5428	int i;
5429	char *cmdname;
5430
5431	(void) setlocale(LC_ALL, "");
5432	(void) textdomain(TEXT_DOMAIN);
5433
5434	if ((g_zfs = libzfs_init()) == NULL) {
5435		(void) fprintf(stderr, gettext("internal error: failed to "
5436		    "initialize ZFS library\n"));
5437		return (1);
5438	}
5439
5440	libzfs_print_on_error(g_zfs, B_TRUE);
5441
5442	opterr = 0;
5443
5444	/*
5445	 * Make sure the user has specified some command.
5446	 */
5447	if (argc < 2) {
5448		(void) fprintf(stderr, gettext("missing command\n"));
5449		usage(B_FALSE);
5450	}
5451
5452	cmdname = argv[1];
5453
5454	/*
5455	 * Special case '-?'
5456	 */
5457	if (strcmp(cmdname, "-?") == 0)
5458		usage(B_TRUE);
5459
5460	zfs_save_arguments(argc, argv, history_str, sizeof (history_str));
5461
5462	/*
5463	 * Run the appropriate command.
5464	 */
5465	if (find_command_idx(cmdname, &i) == 0) {
5466		current_command = &command_table[i];
5467		ret = command_table[i].func(argc - 1, argv + 1);
5468	} else if (strchr(cmdname, '=')) {
5469		verify(find_command_idx("set", &i) == 0);
5470		current_command = &command_table[i];
5471		ret = command_table[i].func(argc, argv);
5472	} else if (strcmp(cmdname, "freeze") == 0 && argc == 3) {
5473		/*
5474		 * 'freeze' is a vile debugging abomination, so we treat
5475		 * it as such.
5476		 */
5477		zfs_cmd_t zc = { 0 };
5478		(void) strlcpy(zc.zc_name, argv[2], sizeof (zc.zc_name));
5479		return (!!zfs_ioctl(g_zfs, ZFS_IOC_POOL_FREEZE, &zc));
5480	} else {
5481		(void) fprintf(stderr, gettext("unrecognized "
5482		    "command '%s'\n"), cmdname);
5483		usage(B_FALSE);
5484	}
5485
5486	if (ret == 0 && log_history)
5487		(void) zpool_log_history(g_zfs, history_str);
5488
5489	libzfs_fini(g_zfs);
5490
5491	/*
5492	 * The 'ZFS_ABORT' environment variable causes us to dump core on exit
5493	 * for the purposes of running ::findleaks.
5494	 */
5495	if (getenv("ZFS_ABORT") != NULL) {
5496		(void) printf("dumping core by request\n");
5497		abort();
5498	}
5499
5500	return (ret);
5501}
5502