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