xref: /titanic_44/usr/src/lib/libzfs/common/libzfs_pool.c (revision 448b8615fe9e8af757530284920a235430ead7e8)
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 2008 Sun Microsystems, Inc.  All rights reserved.
24  * Use is subject to license terms.
25  */
26 
27 #pragma ident	"%Z%%M%	%I%	%E% SMI"
28 
29 #include <alloca.h>
30 #include <assert.h>
31 #include <ctype.h>
32 #include <errno.h>
33 #include <devid.h>
34 #include <dirent.h>
35 #include <fcntl.h>
36 #include <libintl.h>
37 #include <stdio.h>
38 #include <stdlib.h>
39 #include <strings.h>
40 #include <unistd.h>
41 #include <sys/efi_partition.h>
42 #include <sys/vtoc.h>
43 #include <sys/zfs_ioctl.h>
44 #include <sys/zio.h>
45 #include <strings.h>
46 
47 #include "zfs_namecheck.h"
48 #include "zfs_prop.h"
49 #include "libzfs_impl.h"
50 
51 
52 /*
53  * ====================================================================
54  *   zpool property functions
55  * ====================================================================
56  */
57 
58 static int
59 zpool_get_all_props(zpool_handle_t *zhp)
60 {
61 	zfs_cmd_t zc = { 0 };
62 	libzfs_handle_t *hdl = zhp->zpool_hdl;
63 
64 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
65 
66 	if (zcmd_alloc_dst_nvlist(hdl, &zc, 0) != 0)
67 		return (-1);
68 
69 	while (ioctl(hdl->libzfs_fd, ZFS_IOC_POOL_GET_PROPS, &zc) != 0) {
70 		if (errno == ENOMEM) {
71 			if (zcmd_expand_dst_nvlist(hdl, &zc) != 0) {
72 				zcmd_free_nvlists(&zc);
73 				return (-1);
74 			}
75 		} else {
76 			zcmd_free_nvlists(&zc);
77 			return (-1);
78 		}
79 	}
80 
81 	if (zcmd_read_dst_nvlist(hdl, &zc, &zhp->zpool_props) != 0) {
82 		zcmd_free_nvlists(&zc);
83 		return (-1);
84 	}
85 
86 	zcmd_free_nvlists(&zc);
87 
88 	return (0);
89 }
90 
91 static int
92 zpool_props_refresh(zpool_handle_t *zhp)
93 {
94 	nvlist_t *old_props;
95 
96 	old_props = zhp->zpool_props;
97 
98 	if (zpool_get_all_props(zhp) != 0)
99 		return (-1);
100 
101 	nvlist_free(old_props);
102 	return (0);
103 }
104 
105 static char *
106 zpool_get_prop_string(zpool_handle_t *zhp, zpool_prop_t prop,
107     zprop_source_t *src)
108 {
109 	nvlist_t *nv, *nvl;
110 	uint64_t ival;
111 	char *value;
112 	zprop_source_t source;
113 
114 	nvl = zhp->zpool_props;
115 	if (nvlist_lookup_nvlist(nvl, zpool_prop_to_name(prop), &nv) == 0) {
116 		verify(nvlist_lookup_uint64(nv, ZPROP_SOURCE, &ival) == 0);
117 		source = ival;
118 		verify(nvlist_lookup_string(nv, ZPROP_VALUE, &value) == 0);
119 	} else {
120 		source = ZPROP_SRC_DEFAULT;
121 		if ((value = (char *)zpool_prop_default_string(prop)) == NULL)
122 			value = "-";
123 	}
124 
125 	if (src)
126 		*src = source;
127 
128 	return (value);
129 }
130 
131 uint64_t
132 zpool_get_prop_int(zpool_handle_t *zhp, zpool_prop_t prop, zprop_source_t *src)
133 {
134 	nvlist_t *nv, *nvl;
135 	uint64_t value;
136 	zprop_source_t source;
137 
138 	if (zhp->zpool_props == NULL && zpool_get_all_props(zhp))
139 		return (zpool_prop_default_numeric(prop));
140 
141 	nvl = zhp->zpool_props;
142 	if (nvlist_lookup_nvlist(nvl, zpool_prop_to_name(prop), &nv) == 0) {
143 		verify(nvlist_lookup_uint64(nv, ZPROP_SOURCE, &value) == 0);
144 		source = value;
145 		verify(nvlist_lookup_uint64(nv, ZPROP_VALUE, &value) == 0);
146 	} else {
147 		source = ZPROP_SRC_DEFAULT;
148 		value = zpool_prop_default_numeric(prop);
149 	}
150 
151 	if (src)
152 		*src = source;
153 
154 	return (value);
155 }
156 
157 /*
158  * Map VDEV STATE to printed strings.
159  */
160 char *
161 zpool_state_to_name(vdev_state_t state, vdev_aux_t aux)
162 {
163 	switch (state) {
164 	case VDEV_STATE_CLOSED:
165 	case VDEV_STATE_OFFLINE:
166 		return (gettext("OFFLINE"));
167 	case VDEV_STATE_REMOVED:
168 		return (gettext("REMOVED"));
169 	case VDEV_STATE_CANT_OPEN:
170 		if (aux == VDEV_AUX_CORRUPT_DATA)
171 			return (gettext("FAULTED"));
172 		else
173 			return (gettext("UNAVAIL"));
174 	case VDEV_STATE_FAULTED:
175 		return (gettext("FAULTED"));
176 	case VDEV_STATE_DEGRADED:
177 		return (gettext("DEGRADED"));
178 	case VDEV_STATE_HEALTHY:
179 		return (gettext("ONLINE"));
180 	}
181 
182 	return (gettext("UNKNOWN"));
183 }
184 
185 /*
186  * Get a zpool property value for 'prop' and return the value in
187  * a pre-allocated buffer.
188  */
189 int
190 zpool_get_prop(zpool_handle_t *zhp, zpool_prop_t prop, char *buf, size_t len,
191     zprop_source_t *srctype)
192 {
193 	uint64_t intval;
194 	const char *strval;
195 	zprop_source_t src = ZPROP_SRC_NONE;
196 	nvlist_t *nvroot;
197 	vdev_stat_t *vs;
198 	uint_t vsc;
199 
200 	if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) {
201 		if (prop == ZPOOL_PROP_NAME)
202 			(void) strlcpy(buf, zpool_get_name(zhp), len);
203 		else if (prop == ZPOOL_PROP_HEALTH)
204 			(void) strlcpy(buf, "FAULTED", len);
205 		else
206 			(void) strlcpy(buf, "-", len);
207 		return (0);
208 	}
209 
210 	if (zhp->zpool_props == NULL && zpool_get_all_props(zhp) &&
211 	    prop != ZPOOL_PROP_NAME)
212 		return (-1);
213 
214 	switch (zpool_prop_get_type(prop)) {
215 	case PROP_TYPE_STRING:
216 		(void) strlcpy(buf, zpool_get_prop_string(zhp, prop, &src),
217 		    len);
218 		break;
219 
220 	case PROP_TYPE_NUMBER:
221 		intval = zpool_get_prop_int(zhp, prop, &src);
222 
223 		switch (prop) {
224 		case ZPOOL_PROP_SIZE:
225 		case ZPOOL_PROP_USED:
226 		case ZPOOL_PROP_AVAILABLE:
227 			(void) zfs_nicenum(intval, buf, len);
228 			break;
229 
230 		case ZPOOL_PROP_CAPACITY:
231 			(void) snprintf(buf, len, "%llu%%",
232 			    (u_longlong_t)intval);
233 			break;
234 
235 		case ZPOOL_PROP_HEALTH:
236 			verify(nvlist_lookup_nvlist(zpool_get_config(zhp, NULL),
237 			    ZPOOL_CONFIG_VDEV_TREE, &nvroot) == 0);
238 			verify(nvlist_lookup_uint64_array(nvroot,
239 			    ZPOOL_CONFIG_STATS, (uint64_t **)&vs, &vsc) == 0);
240 
241 			(void) strlcpy(buf, zpool_state_to_name(intval,
242 			    vs->vs_aux), len);
243 			break;
244 		default:
245 			(void) snprintf(buf, len, "%llu", intval);
246 		}
247 		break;
248 
249 	case PROP_TYPE_INDEX:
250 		intval = zpool_get_prop_int(zhp, prop, &src);
251 		if (zpool_prop_index_to_string(prop, intval, &strval)
252 		    != 0)
253 			return (-1);
254 		(void) strlcpy(buf, strval, len);
255 		break;
256 
257 	default:
258 		abort();
259 	}
260 
261 	if (srctype)
262 		*srctype = src;
263 
264 	return (0);
265 }
266 
267 /*
268  * Check if the bootfs name has the same pool name as it is set to.
269  * Assuming bootfs is a valid dataset name.
270  */
271 static boolean_t
272 bootfs_name_valid(const char *pool, char *bootfs)
273 {
274 	int len = strlen(pool);
275 
276 	if (!zfs_name_valid(bootfs, ZFS_TYPE_FILESYSTEM))
277 		return (B_FALSE);
278 
279 	if (strncmp(pool, bootfs, len) == 0 &&
280 	    (bootfs[len] == '/' || bootfs[len] == '\0'))
281 		return (B_TRUE);
282 
283 	return (B_FALSE);
284 }
285 
286 /*
287  * Given an nvlist of zpool properties to be set, validate that they are
288  * correct, and parse any numeric properties (index, boolean, etc) if they are
289  * specified as strings.
290  */
291 static nvlist_t *
292 zpool_validate_properties(libzfs_handle_t *hdl, const char *poolname,
293     nvlist_t *props, uint64_t version, boolean_t create_or_import, char *errbuf)
294 {
295 	nvpair_t *elem;
296 	nvlist_t *retprops;
297 	zpool_prop_t prop;
298 	char *strval;
299 	uint64_t intval;
300 	char *slash;
301 	struct stat64 statbuf;
302 
303 	if (nvlist_alloc(&retprops, NV_UNIQUE_NAME, 0) != 0) {
304 		(void) no_memory(hdl);
305 		return (NULL);
306 	}
307 
308 	elem = NULL;
309 	while ((elem = nvlist_next_nvpair(props, elem)) != NULL) {
310 		const char *propname = nvpair_name(elem);
311 
312 		/*
313 		 * Make sure this property is valid and applies to this type.
314 		 */
315 		if ((prop = zpool_name_to_prop(propname)) == ZPROP_INVAL) {
316 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
317 			    "invalid property '%s'"), propname);
318 			(void) zfs_error(hdl, EZFS_BADPROP, errbuf);
319 			goto error;
320 		}
321 
322 		if (zpool_prop_readonly(prop)) {
323 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "'%s' "
324 			    "is readonly"), propname);
325 			(void) zfs_error(hdl, EZFS_PROPREADONLY, errbuf);
326 			goto error;
327 		}
328 
329 		if (zprop_parse_value(hdl, elem, prop, ZFS_TYPE_POOL, retprops,
330 		    &strval, &intval, errbuf) != 0)
331 			goto error;
332 
333 		/*
334 		 * Perform additional checking for specific properties.
335 		 */
336 		switch (prop) {
337 		case ZPOOL_PROP_VERSION:
338 			if (intval < version || intval > SPA_VERSION) {
339 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
340 				    "property '%s' number %d is invalid."),
341 				    propname, intval);
342 				(void) zfs_error(hdl, EZFS_BADVERSION, errbuf);
343 				goto error;
344 			}
345 			break;
346 
347 		case ZPOOL_PROP_BOOTFS:
348 			if (create_or_import) {
349 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
350 				    "property '%s' cannot be set at creation "
351 				    "or import time"), propname);
352 				(void) zfs_error(hdl, EZFS_BADPROP, errbuf);
353 				goto error;
354 			}
355 
356 			if (version < SPA_VERSION_BOOTFS) {
357 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
358 				    "pool must be upgraded to support "
359 				    "'%s' property"), propname);
360 				(void) zfs_error(hdl, EZFS_BADVERSION, errbuf);
361 				goto error;
362 			}
363 
364 			/*
365 			 * bootfs property value has to be a dataset name and
366 			 * the dataset has to be in the same pool as it sets to.
367 			 */
368 			if (strval[0] != '\0' && !bootfs_name_valid(poolname,
369 			    strval)) {
370 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "'%s' "
371 				    "is an invalid name"), strval);
372 				(void) zfs_error(hdl, EZFS_INVALIDNAME, errbuf);
373 				goto error;
374 			}
375 			break;
376 
377 		case ZPOOL_PROP_ALTROOT:
378 			if (!create_or_import) {
379 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
380 				    "property '%s' can only be set during pool "
381 				    "creation or import"), propname);
382 				(void) zfs_error(hdl, EZFS_BADPROP, errbuf);
383 				goto error;
384 			}
385 
386 			if (strval[0] != '/') {
387 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
388 				    "bad alternate root '%s'"), strval);
389 				(void) zfs_error(hdl, EZFS_BADPATH, errbuf);
390 				goto error;
391 			}
392 			break;
393 
394 		case ZPOOL_PROP_CACHEFILE:
395 			if (strval[0] == '\0')
396 				break;
397 
398 			if (strcmp(strval, "none") == 0)
399 				break;
400 
401 			if (strval[0] != '/') {
402 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
403 				    "property '%s' must be empty, an "
404 				    "absolute path, or 'none'"), propname);
405 				(void) zfs_error(hdl, EZFS_BADPATH, errbuf);
406 				goto error;
407 			}
408 
409 			slash = strrchr(strval, '/');
410 
411 			if (slash[1] == '\0' || strcmp(slash, "/.") == 0 ||
412 			    strcmp(slash, "/..") == 0) {
413 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
414 				    "'%s' is not a valid file"), strval);
415 				(void) zfs_error(hdl, EZFS_BADPATH, errbuf);
416 				goto error;
417 			}
418 
419 			*slash = '\0';
420 
421 			if (strval[0] != '\0' &&
422 			    (stat64(strval, &statbuf) != 0 ||
423 			    !S_ISDIR(statbuf.st_mode))) {
424 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
425 				    "'%s' is not a valid directory"),
426 				    strval);
427 				(void) zfs_error(hdl, EZFS_BADPATH, errbuf);
428 				goto error;
429 			}
430 
431 			*slash = '/';
432 			break;
433 		}
434 	}
435 
436 	return (retprops);
437 error:
438 	nvlist_free(retprops);
439 	return (NULL);
440 }
441 
442 /*
443  * Set zpool property : propname=propval.
444  */
445 int
446 zpool_set_prop(zpool_handle_t *zhp, const char *propname, const char *propval)
447 {
448 	zfs_cmd_t zc = { 0 };
449 	int ret = -1;
450 	char errbuf[1024];
451 	nvlist_t *nvl = NULL;
452 	nvlist_t *realprops;
453 	uint64_t version;
454 
455 	(void) snprintf(errbuf, sizeof (errbuf),
456 	    dgettext(TEXT_DOMAIN, "cannot set property for '%s'"),
457 	    zhp->zpool_name);
458 
459 	if (zhp->zpool_props == NULL && zpool_get_all_props(zhp))
460 		return (zfs_error(zhp->zpool_hdl, EZFS_POOLPROPS, errbuf));
461 
462 	if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0)
463 		return (no_memory(zhp->zpool_hdl));
464 
465 	if (nvlist_add_string(nvl, propname, propval) != 0) {
466 		nvlist_free(nvl);
467 		return (no_memory(zhp->zpool_hdl));
468 	}
469 
470 	version = zpool_get_prop_int(zhp, ZPOOL_PROP_VERSION, NULL);
471 	if ((realprops = zpool_validate_properties(zhp->zpool_hdl,
472 	    zhp->zpool_name, nvl, version, B_FALSE, errbuf)) == NULL) {
473 		nvlist_free(nvl);
474 		return (-1);
475 	}
476 
477 	nvlist_free(nvl);
478 	nvl = realprops;
479 
480 	/*
481 	 * Execute the corresponding ioctl() to set this property.
482 	 */
483 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
484 
485 	if (zcmd_write_src_nvlist(zhp->zpool_hdl, &zc, nvl) != 0) {
486 		nvlist_free(nvl);
487 		return (-1);
488 	}
489 
490 	ret = zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_POOL_SET_PROPS, &zc);
491 
492 	zcmd_free_nvlists(&zc);
493 	nvlist_free(nvl);
494 
495 	if (ret)
496 		(void) zpool_standard_error(zhp->zpool_hdl, errno, errbuf);
497 	else
498 		(void) zpool_props_refresh(zhp);
499 
500 	return (ret);
501 }
502 
503 int
504 zpool_expand_proplist(zpool_handle_t *zhp, zprop_list_t **plp)
505 {
506 	libzfs_handle_t *hdl = zhp->zpool_hdl;
507 	zprop_list_t *entry;
508 	char buf[ZFS_MAXPROPLEN];
509 
510 	if (zprop_expand_list(hdl, plp, ZFS_TYPE_POOL) != 0)
511 		return (-1);
512 
513 	for (entry = *plp; entry != NULL; entry = entry->pl_next) {
514 
515 		if (entry->pl_fixed)
516 			continue;
517 
518 		if (entry->pl_prop != ZPROP_INVAL &&
519 		    zpool_get_prop(zhp, entry->pl_prop, buf, sizeof (buf),
520 		    NULL) == 0) {
521 			if (strlen(buf) > entry->pl_width)
522 				entry->pl_width = strlen(buf);
523 		}
524 	}
525 
526 	return (0);
527 }
528 
529 
530 /*
531  * Validate the given pool name, optionally putting an extended error message in
532  * 'buf'.
533  */
534 boolean_t
535 zpool_name_valid(libzfs_handle_t *hdl, boolean_t isopen, const char *pool)
536 {
537 	namecheck_err_t why;
538 	char what;
539 	int ret;
540 
541 	ret = pool_namecheck(pool, &why, &what);
542 
543 	/*
544 	 * The rules for reserved pool names were extended at a later point.
545 	 * But we need to support users with existing pools that may now be
546 	 * invalid.  So we only check for this expanded set of names during a
547 	 * create (or import), and only in userland.
548 	 */
549 	if (ret == 0 && !isopen &&
550 	    (strncmp(pool, "mirror", 6) == 0 ||
551 	    strncmp(pool, "raidz", 5) == 0 ||
552 	    strncmp(pool, "spare", 5) == 0 ||
553 	    strcmp(pool, "log") == 0)) {
554 		if (hdl != NULL)
555 			zfs_error_aux(hdl,
556 			    dgettext(TEXT_DOMAIN, "name is reserved"));
557 		return (B_FALSE);
558 	}
559 
560 
561 	if (ret != 0) {
562 		if (hdl != NULL) {
563 			switch (why) {
564 			case NAME_ERR_TOOLONG:
565 				zfs_error_aux(hdl,
566 				    dgettext(TEXT_DOMAIN, "name is too long"));
567 				break;
568 
569 			case NAME_ERR_INVALCHAR:
570 				zfs_error_aux(hdl,
571 				    dgettext(TEXT_DOMAIN, "invalid character "
572 				    "'%c' in pool name"), what);
573 				break;
574 
575 			case NAME_ERR_NOLETTER:
576 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
577 				    "name must begin with a letter"));
578 				break;
579 
580 			case NAME_ERR_RESERVED:
581 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
582 				    "name is reserved"));
583 				break;
584 
585 			case NAME_ERR_DISKLIKE:
586 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
587 				    "pool name is reserved"));
588 				break;
589 
590 			case NAME_ERR_LEADING_SLASH:
591 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
592 				    "leading slash in name"));
593 				break;
594 
595 			case NAME_ERR_EMPTY_COMPONENT:
596 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
597 				    "empty component in name"));
598 				break;
599 
600 			case NAME_ERR_TRAILING_SLASH:
601 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
602 				    "trailing slash in name"));
603 				break;
604 
605 			case NAME_ERR_MULTIPLE_AT:
606 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
607 				    "multiple '@' delimiters in name"));
608 				break;
609 
610 			}
611 		}
612 		return (B_FALSE);
613 	}
614 
615 	return (B_TRUE);
616 }
617 
618 /*
619  * Open a handle to the given pool, even if the pool is currently in the FAULTED
620  * state.
621  */
622 zpool_handle_t *
623 zpool_open_canfail(libzfs_handle_t *hdl, const char *pool)
624 {
625 	zpool_handle_t *zhp;
626 	boolean_t missing;
627 
628 	/*
629 	 * Make sure the pool name is valid.
630 	 */
631 	if (!zpool_name_valid(hdl, B_TRUE, pool)) {
632 		(void) zfs_error_fmt(hdl, EZFS_INVALIDNAME,
633 		    dgettext(TEXT_DOMAIN, "cannot open '%s'"),
634 		    pool);
635 		return (NULL);
636 	}
637 
638 	if ((zhp = zfs_alloc(hdl, sizeof (zpool_handle_t))) == NULL)
639 		return (NULL);
640 
641 	zhp->zpool_hdl = hdl;
642 	(void) strlcpy(zhp->zpool_name, pool, sizeof (zhp->zpool_name));
643 
644 	if (zpool_refresh_stats(zhp, &missing) != 0) {
645 		zpool_close(zhp);
646 		return (NULL);
647 	}
648 
649 	if (missing) {
650 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "no such pool"));
651 		(void) zfs_error_fmt(hdl, EZFS_NOENT,
652 		    dgettext(TEXT_DOMAIN, "cannot open '%s'"), pool);
653 		zpool_close(zhp);
654 		return (NULL);
655 	}
656 
657 	return (zhp);
658 }
659 
660 /*
661  * Like the above, but silent on error.  Used when iterating over pools (because
662  * the configuration cache may be out of date).
663  */
664 int
665 zpool_open_silent(libzfs_handle_t *hdl, const char *pool, zpool_handle_t **ret)
666 {
667 	zpool_handle_t *zhp;
668 	boolean_t missing;
669 
670 	if ((zhp = zfs_alloc(hdl, sizeof (zpool_handle_t))) == NULL)
671 		return (-1);
672 
673 	zhp->zpool_hdl = hdl;
674 	(void) strlcpy(zhp->zpool_name, pool, sizeof (zhp->zpool_name));
675 
676 	if (zpool_refresh_stats(zhp, &missing) != 0) {
677 		zpool_close(zhp);
678 		return (-1);
679 	}
680 
681 	if (missing) {
682 		zpool_close(zhp);
683 		*ret = NULL;
684 		return (0);
685 	}
686 
687 	*ret = zhp;
688 	return (0);
689 }
690 
691 /*
692  * Similar to zpool_open_canfail(), but refuses to open pools in the faulted
693  * state.
694  */
695 zpool_handle_t *
696 zpool_open(libzfs_handle_t *hdl, const char *pool)
697 {
698 	zpool_handle_t *zhp;
699 
700 	if ((zhp = zpool_open_canfail(hdl, pool)) == NULL)
701 		return (NULL);
702 
703 	if (zhp->zpool_state == POOL_STATE_UNAVAIL) {
704 		(void) zfs_error_fmt(hdl, EZFS_POOLUNAVAIL,
705 		    dgettext(TEXT_DOMAIN, "cannot open '%s'"), zhp->zpool_name);
706 		zpool_close(zhp);
707 		return (NULL);
708 	}
709 
710 	return (zhp);
711 }
712 
713 /*
714  * Close the handle.  Simply frees the memory associated with the handle.
715  */
716 void
717 zpool_close(zpool_handle_t *zhp)
718 {
719 	if (zhp->zpool_config)
720 		nvlist_free(zhp->zpool_config);
721 	if (zhp->zpool_old_config)
722 		nvlist_free(zhp->zpool_old_config);
723 	if (zhp->zpool_props)
724 		nvlist_free(zhp->zpool_props);
725 	free(zhp);
726 }
727 
728 /*
729  * Return the name of the pool.
730  */
731 const char *
732 zpool_get_name(zpool_handle_t *zhp)
733 {
734 	return (zhp->zpool_name);
735 }
736 
737 
738 /*
739  * Return the state of the pool (ACTIVE or UNAVAILABLE)
740  */
741 int
742 zpool_get_state(zpool_handle_t *zhp)
743 {
744 	return (zhp->zpool_state);
745 }
746 
747 /*
748  * Create the named pool, using the provided vdev list.  It is assumed
749  * that the consumer has already validated the contents of the nvlist, so we
750  * don't have to worry about error semantics.
751  */
752 int
753 zpool_create(libzfs_handle_t *hdl, const char *pool, nvlist_t *nvroot,
754     nvlist_t *props)
755 {
756 	zfs_cmd_t zc = { 0 };
757 	char msg[1024];
758 	char *altroot;
759 
760 	(void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN,
761 	    "cannot create '%s'"), pool);
762 
763 	if (!zpool_name_valid(hdl, B_FALSE, pool))
764 		return (zfs_error(hdl, EZFS_INVALIDNAME, msg));
765 
766 	if (zcmd_write_conf_nvlist(hdl, &zc, nvroot) != 0)
767 		return (-1);
768 
769 	if (props && (props = zpool_validate_properties(hdl, pool, props,
770 	    SPA_VERSION_1, B_TRUE, msg)) == NULL)
771 		return (-1);
772 
773 	if (props && zcmd_write_src_nvlist(hdl, &zc, props) != 0) {
774 		nvlist_free(props);
775 		return (-1);
776 	}
777 
778 	(void) strlcpy(zc.zc_name, pool, sizeof (zc.zc_name));
779 
780 	if (zfs_ioctl(hdl, ZFS_IOC_POOL_CREATE, &zc) != 0) {
781 
782 		zcmd_free_nvlists(&zc);
783 		nvlist_free(props);
784 
785 		switch (errno) {
786 		case EBUSY:
787 			/*
788 			 * This can happen if the user has specified the same
789 			 * device multiple times.  We can't reliably detect this
790 			 * until we try to add it and see we already have a
791 			 * label.
792 			 */
793 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
794 			    "one or more vdevs refer to the same device"));
795 			return (zfs_error(hdl, EZFS_BADDEV, msg));
796 
797 		case EOVERFLOW:
798 			/*
799 			 * This occurs when one of the devices is below
800 			 * SPA_MINDEVSIZE.  Unfortunately, we can't detect which
801 			 * device was the problem device since there's no
802 			 * reliable way to determine device size from userland.
803 			 */
804 			{
805 				char buf[64];
806 
807 				zfs_nicenum(SPA_MINDEVSIZE, buf, sizeof (buf));
808 
809 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
810 				    "one or more devices is less than the "
811 				    "minimum size (%s)"), buf);
812 			}
813 			return (zfs_error(hdl, EZFS_BADDEV, msg));
814 
815 		case ENOSPC:
816 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
817 			    "one or more devices is out of space"));
818 			return (zfs_error(hdl, EZFS_BADDEV, msg));
819 
820 		case ENOTBLK:
821 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
822 			    "cache device must be a disk or disk slice"));
823 			return (zfs_error(hdl, EZFS_BADDEV, msg));
824 
825 		default:
826 			return (zpool_standard_error(hdl, errno, msg));
827 		}
828 	}
829 
830 	/*
831 	 * If this is an alternate root pool, then we automatically set the
832 	 * mountpoint of the root dataset to be '/'.
833 	 */
834 	if (nvlist_lookup_string(props, zpool_prop_to_name(ZPOOL_PROP_ALTROOT),
835 	    &altroot) == 0) {
836 		zfs_handle_t *zhp;
837 
838 		verify((zhp = zfs_open(hdl, pool, ZFS_TYPE_DATASET)) != NULL);
839 		verify(zfs_prop_set(zhp, zfs_prop_to_name(ZFS_PROP_MOUNTPOINT),
840 		    "/") == 0);
841 
842 		zfs_close(zhp);
843 	}
844 
845 	zcmd_free_nvlists(&zc);
846 	nvlist_free(props);
847 	return (0);
848 }
849 
850 /*
851  * Destroy the given pool.  It is up to the caller to ensure that there are no
852  * datasets left in the pool.
853  */
854 int
855 zpool_destroy(zpool_handle_t *zhp)
856 {
857 	zfs_cmd_t zc = { 0 };
858 	zfs_handle_t *zfp = NULL;
859 	libzfs_handle_t *hdl = zhp->zpool_hdl;
860 	char msg[1024];
861 
862 	if (zhp->zpool_state == POOL_STATE_ACTIVE &&
863 	    (zfp = zfs_open(zhp->zpool_hdl, zhp->zpool_name,
864 	    ZFS_TYPE_FILESYSTEM)) == NULL)
865 		return (-1);
866 
867 	if (zpool_remove_zvol_links(zhp) != 0)
868 		return (-1);
869 
870 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
871 
872 	if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_POOL_DESTROY, &zc) != 0) {
873 		(void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN,
874 		    "cannot destroy '%s'"), zhp->zpool_name);
875 
876 		if (errno == EROFS) {
877 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
878 			    "one or more devices is read only"));
879 			(void) zfs_error(hdl, EZFS_BADDEV, msg);
880 		} else {
881 			(void) zpool_standard_error(hdl, errno, msg);
882 		}
883 
884 		if (zfp)
885 			zfs_close(zfp);
886 		return (-1);
887 	}
888 
889 	if (zfp) {
890 		remove_mountpoint(zfp);
891 		zfs_close(zfp);
892 	}
893 
894 	return (0);
895 }
896 
897 /*
898  * Add the given vdevs to the pool.  The caller must have already performed the
899  * necessary verification to ensure that the vdev specification is well-formed.
900  */
901 int
902 zpool_add(zpool_handle_t *zhp, nvlist_t *nvroot)
903 {
904 	zfs_cmd_t zc = { 0 };
905 	int ret;
906 	libzfs_handle_t *hdl = zhp->zpool_hdl;
907 	char msg[1024];
908 	nvlist_t **spares, **l2cache;
909 	uint_t nspares, nl2cache;
910 
911 	(void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN,
912 	    "cannot add to '%s'"), zhp->zpool_name);
913 
914 	if (zpool_get_prop_int(zhp, ZPOOL_PROP_VERSION, NULL) <
915 	    SPA_VERSION_SPARES &&
916 	    nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_SPARES,
917 	    &spares, &nspares) == 0) {
918 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "pool must be "
919 		    "upgraded to add hot spares"));
920 		return (zfs_error(hdl, EZFS_BADVERSION, msg));
921 	}
922 
923 	if (zpool_get_prop_int(zhp, ZPOOL_PROP_VERSION, NULL) <
924 	    SPA_VERSION_L2CACHE &&
925 	    nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_L2CACHE,
926 	    &l2cache, &nl2cache) == 0) {
927 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "pool must be "
928 		    "upgraded to add cache devices"));
929 		return (zfs_error(hdl, EZFS_BADVERSION, msg));
930 	}
931 
932 	if (zcmd_write_conf_nvlist(hdl, &zc, nvroot) != 0)
933 		return (-1);
934 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
935 
936 	if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_VDEV_ADD, &zc) != 0) {
937 		switch (errno) {
938 		case EBUSY:
939 			/*
940 			 * This can happen if the user has specified the same
941 			 * device multiple times.  We can't reliably detect this
942 			 * until we try to add it and see we already have a
943 			 * label.
944 			 */
945 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
946 			    "one or more vdevs refer to the same device"));
947 			(void) zfs_error(hdl, EZFS_BADDEV, msg);
948 			break;
949 
950 		case EOVERFLOW:
951 			/*
952 			 * This occurrs when one of the devices is below
953 			 * SPA_MINDEVSIZE.  Unfortunately, we can't detect which
954 			 * device was the problem device since there's no
955 			 * reliable way to determine device size from userland.
956 			 */
957 			{
958 				char buf[64];
959 
960 				zfs_nicenum(SPA_MINDEVSIZE, buf, sizeof (buf));
961 
962 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
963 				    "device is less than the minimum "
964 				    "size (%s)"), buf);
965 			}
966 			(void) zfs_error(hdl, EZFS_BADDEV, msg);
967 			break;
968 
969 		case ENOTSUP:
970 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
971 			    "pool must be upgraded to add these vdevs"));
972 			(void) zfs_error(hdl, EZFS_BADVERSION, msg);
973 			break;
974 
975 		case EDOM:
976 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
977 			    "root pool can not have multiple vdevs"
978 			    " or separate logs"));
979 			(void) zfs_error(hdl, EZFS_POOL_NOTSUP, msg);
980 			break;
981 
982 		case ENOTBLK:
983 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
984 			    "cache device must be a disk or disk slice"));
985 			(void) zfs_error(hdl, EZFS_BADDEV, msg);
986 			break;
987 
988 		default:
989 			(void) zpool_standard_error(hdl, errno, msg);
990 		}
991 
992 		ret = -1;
993 	} else {
994 		ret = 0;
995 	}
996 
997 	zcmd_free_nvlists(&zc);
998 
999 	return (ret);
1000 }
1001 
1002 /*
1003  * Exports the pool from the system.  The caller must ensure that there are no
1004  * mounted datasets in the pool.
1005  */
1006 int
1007 zpool_export(zpool_handle_t *zhp)
1008 {
1009 	zfs_cmd_t zc = { 0 };
1010 
1011 	if (zpool_remove_zvol_links(zhp) != 0)
1012 		return (-1);
1013 
1014 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1015 
1016 	if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_POOL_EXPORT, &zc) != 0)
1017 		return (zpool_standard_error_fmt(zhp->zpool_hdl, errno,
1018 		    dgettext(TEXT_DOMAIN, "cannot export '%s'"),
1019 		    zhp->zpool_name));
1020 	return (0);
1021 }
1022 
1023 /*
1024  * zpool_import() is a contracted interface. Should be kept the same
1025  * if possible.
1026  *
1027  * Applications should use zpool_import_props() to import a pool with
1028  * new properties value to be set.
1029  */
1030 int
1031 zpool_import(libzfs_handle_t *hdl, nvlist_t *config, const char *newname,
1032     char *altroot)
1033 {
1034 	nvlist_t *props = NULL;
1035 	int ret;
1036 
1037 	if (altroot != NULL) {
1038 		if (nvlist_alloc(&props, NV_UNIQUE_NAME, 0) != 0) {
1039 			return (zfs_error_fmt(hdl, EZFS_NOMEM,
1040 			    dgettext(TEXT_DOMAIN, "cannot import '%s'"),
1041 			    newname));
1042 		}
1043 
1044 		if (nvlist_add_string(props,
1045 		    zpool_prop_to_name(ZPOOL_PROP_ALTROOT), altroot) != 0) {
1046 			nvlist_free(props);
1047 			return (zfs_error_fmt(hdl, EZFS_NOMEM,
1048 			    dgettext(TEXT_DOMAIN, "cannot import '%s'"),
1049 			    newname));
1050 		}
1051 	}
1052 
1053 	ret = zpool_import_props(hdl, config, newname, props, B_FALSE);
1054 	if (props)
1055 		nvlist_free(props);
1056 	return (ret);
1057 }
1058 
1059 /*
1060  * Import the given pool using the known configuration and a list of
1061  * properties to be set. The configuration should have come from
1062  * zpool_find_import(). The 'newname' parameters control whether the pool
1063  * is imported with a different name.
1064  */
1065 int
1066 zpool_import_props(libzfs_handle_t *hdl, nvlist_t *config, const char *newname,
1067     nvlist_t *props, boolean_t importfaulted)
1068 {
1069 	zfs_cmd_t zc = { 0 };
1070 	char *thename;
1071 	char *origname;
1072 	int ret;
1073 	char errbuf[1024];
1074 
1075 	verify(nvlist_lookup_string(config, ZPOOL_CONFIG_POOL_NAME,
1076 	    &origname) == 0);
1077 
1078 	(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
1079 	    "cannot import pool '%s'"), origname);
1080 
1081 	if (newname != NULL) {
1082 		if (!zpool_name_valid(hdl, B_FALSE, newname))
1083 			return (zfs_error_fmt(hdl, EZFS_INVALIDNAME,
1084 			    dgettext(TEXT_DOMAIN, "cannot import '%s'"),
1085 			    newname));
1086 		thename = (char *)newname;
1087 	} else {
1088 		thename = origname;
1089 	}
1090 
1091 	if (props) {
1092 		uint64_t version;
1093 
1094 		verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
1095 		    &version) == 0);
1096 
1097 		if ((props = zpool_validate_properties(hdl, origname,
1098 		    props, version, B_TRUE, errbuf)) == NULL) {
1099 			return (-1);
1100 		} else if (zcmd_write_src_nvlist(hdl, &zc, props) != 0) {
1101 			nvlist_free(props);
1102 			return (-1);
1103 		}
1104 	}
1105 
1106 	(void) strlcpy(zc.zc_name, thename, sizeof (zc.zc_name));
1107 
1108 	verify(nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_GUID,
1109 	    &zc.zc_guid) == 0);
1110 
1111 	if (zcmd_write_conf_nvlist(hdl, &zc, config) != 0) {
1112 		nvlist_free(props);
1113 		return (-1);
1114 	}
1115 
1116 	zc.zc_cookie = (uint64_t)importfaulted;
1117 	ret = 0;
1118 	if (zfs_ioctl(hdl, ZFS_IOC_POOL_IMPORT, &zc) != 0) {
1119 		char desc[1024];
1120 		if (newname == NULL)
1121 			(void) snprintf(desc, sizeof (desc),
1122 			    dgettext(TEXT_DOMAIN, "cannot import '%s'"),
1123 			    thename);
1124 		else
1125 			(void) snprintf(desc, sizeof (desc),
1126 			    dgettext(TEXT_DOMAIN, "cannot import '%s' as '%s'"),
1127 			    origname, thename);
1128 
1129 		switch (errno) {
1130 		case ENOTSUP:
1131 			/*
1132 			 * Unsupported version.
1133 			 */
1134 			(void) zfs_error(hdl, EZFS_BADVERSION, desc);
1135 			break;
1136 
1137 		case EINVAL:
1138 			(void) zfs_error(hdl, EZFS_INVALCONFIG, desc);
1139 			break;
1140 
1141 		default:
1142 			(void) zpool_standard_error(hdl, errno, desc);
1143 		}
1144 
1145 		ret = -1;
1146 	} else {
1147 		zpool_handle_t *zhp;
1148 
1149 		/*
1150 		 * This should never fail, but play it safe anyway.
1151 		 */
1152 		if (zpool_open_silent(hdl, thename, &zhp) != 0) {
1153 			ret = -1;
1154 		} else if (zhp != NULL) {
1155 			ret = zpool_create_zvol_links(zhp);
1156 			zpool_close(zhp);
1157 		}
1158 
1159 	}
1160 
1161 	zcmd_free_nvlists(&zc);
1162 	nvlist_free(props);
1163 
1164 	return (ret);
1165 }
1166 
1167 /*
1168  * Scrub the pool.
1169  */
1170 int
1171 zpool_scrub(zpool_handle_t *zhp, pool_scrub_type_t type)
1172 {
1173 	zfs_cmd_t zc = { 0 };
1174 	char msg[1024];
1175 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1176 
1177 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1178 	zc.zc_cookie = type;
1179 
1180 	if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_POOL_SCRUB, &zc) == 0)
1181 		return (0);
1182 
1183 	(void) snprintf(msg, sizeof (msg),
1184 	    dgettext(TEXT_DOMAIN, "cannot scrub %s"), zc.zc_name);
1185 
1186 	if (errno == EBUSY)
1187 		return (zfs_error(hdl, EZFS_RESILVERING, msg));
1188 	else
1189 		return (zpool_standard_error(hdl, errno, msg));
1190 }
1191 
1192 /*
1193  * 'avail_spare' is set to TRUE if the provided guid refers to an AVAIL
1194  * spare; but FALSE if its an INUSE spare.
1195  */
1196 static nvlist_t *
1197 vdev_to_nvlist_iter(nvlist_t *nv, const char *search, uint64_t guid,
1198     boolean_t *avail_spare, boolean_t *l2cache)
1199 {
1200 	uint_t c, children;
1201 	nvlist_t **child;
1202 	uint64_t theguid, present;
1203 	char *path;
1204 	uint64_t wholedisk = 0;
1205 	nvlist_t *ret;
1206 
1207 	verify(nvlist_lookup_uint64(nv, ZPOOL_CONFIG_GUID, &theguid) == 0);
1208 
1209 	if (search == NULL &&
1210 	    nvlist_lookup_uint64(nv, ZPOOL_CONFIG_NOT_PRESENT, &present) == 0) {
1211 		/*
1212 		 * If the device has never been present since import, the only
1213 		 * reliable way to match the vdev is by GUID.
1214 		 */
1215 		if (theguid == guid)
1216 			return (nv);
1217 	} else if (search != NULL &&
1218 	    nvlist_lookup_string(nv, ZPOOL_CONFIG_PATH, &path) == 0) {
1219 		(void) nvlist_lookup_uint64(nv, ZPOOL_CONFIG_WHOLE_DISK,
1220 		    &wholedisk);
1221 		if (wholedisk) {
1222 			/*
1223 			 * For whole disks, the internal path has 's0', but the
1224 			 * path passed in by the user doesn't.
1225 			 */
1226 			if (strlen(search) == strlen(path) - 2 &&
1227 			    strncmp(search, path, strlen(search)) == 0)
1228 				return (nv);
1229 		} else if (strcmp(search, path) == 0) {
1230 			return (nv);
1231 		}
1232 	}
1233 
1234 	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_CHILDREN,
1235 	    &child, &children) != 0)
1236 		return (NULL);
1237 
1238 	for (c = 0; c < children; c++)
1239 		if ((ret = vdev_to_nvlist_iter(child[c], search, guid,
1240 		    avail_spare, l2cache)) != NULL)
1241 			return (ret);
1242 
1243 	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_SPARES,
1244 	    &child, &children) == 0) {
1245 		for (c = 0; c < children; c++) {
1246 			if ((ret = vdev_to_nvlist_iter(child[c], search, guid,
1247 			    avail_spare, l2cache)) != NULL) {
1248 				*avail_spare = B_TRUE;
1249 				return (ret);
1250 			}
1251 		}
1252 	}
1253 
1254 	if (nvlist_lookup_nvlist_array(nv, ZPOOL_CONFIG_L2CACHE,
1255 	    &child, &children) == 0) {
1256 		for (c = 0; c < children; c++) {
1257 			if ((ret = vdev_to_nvlist_iter(child[c], search, guid,
1258 			    avail_spare, l2cache)) != NULL) {
1259 				*l2cache = B_TRUE;
1260 				return (ret);
1261 			}
1262 		}
1263 	}
1264 
1265 	return (NULL);
1266 }
1267 
1268 nvlist_t *
1269 zpool_find_vdev(zpool_handle_t *zhp, const char *path, boolean_t *avail_spare,
1270     boolean_t *l2cache)
1271 {
1272 	char buf[MAXPATHLEN];
1273 	const char *search;
1274 	char *end;
1275 	nvlist_t *nvroot;
1276 	uint64_t guid;
1277 
1278 	guid = strtoull(path, &end, 10);
1279 	if (guid != 0 && *end == '\0') {
1280 		search = NULL;
1281 	} else if (path[0] != '/') {
1282 		(void) snprintf(buf, sizeof (buf), "%s%s", "/dev/dsk/", path);
1283 		search = buf;
1284 	} else {
1285 		search = path;
1286 	}
1287 
1288 	verify(nvlist_lookup_nvlist(zhp->zpool_config, ZPOOL_CONFIG_VDEV_TREE,
1289 	    &nvroot) == 0);
1290 
1291 	*avail_spare = B_FALSE;
1292 	*l2cache = B_FALSE;
1293 	return (vdev_to_nvlist_iter(nvroot, search, guid, avail_spare,
1294 	    l2cache));
1295 }
1296 
1297 /*
1298  * Returns TRUE if the given guid corresponds to the given type.
1299  * This is used to check for hot spares (INUSE or not), and level 2 cache
1300  * devices.
1301  */
1302 static boolean_t
1303 is_guid_type(zpool_handle_t *zhp, uint64_t guid, const char *type)
1304 {
1305 	uint64_t target_guid;
1306 	nvlist_t *nvroot;
1307 	nvlist_t **list;
1308 	uint_t count;
1309 	int i;
1310 
1311 	verify(nvlist_lookup_nvlist(zhp->zpool_config, ZPOOL_CONFIG_VDEV_TREE,
1312 	    &nvroot) == 0);
1313 	if (nvlist_lookup_nvlist_array(nvroot, type, &list, &count) == 0) {
1314 		for (i = 0; i < count; i++) {
1315 			verify(nvlist_lookup_uint64(list[i], ZPOOL_CONFIG_GUID,
1316 			    &target_guid) == 0);
1317 			if (guid == target_guid)
1318 				return (B_TRUE);
1319 		}
1320 	}
1321 
1322 	return (B_FALSE);
1323 }
1324 
1325 /*
1326  * Bring the specified vdev online.   The 'flags' parameter is a set of the
1327  * ZFS_ONLINE_* flags.
1328  */
1329 int
1330 zpool_vdev_online(zpool_handle_t *zhp, const char *path, int flags,
1331     vdev_state_t *newstate)
1332 {
1333 	zfs_cmd_t zc = { 0 };
1334 	char msg[1024];
1335 	nvlist_t *tgt;
1336 	boolean_t avail_spare, l2cache;
1337 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1338 
1339 	(void) snprintf(msg, sizeof (msg),
1340 	    dgettext(TEXT_DOMAIN, "cannot online %s"), path);
1341 
1342 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1343 	if ((tgt = zpool_find_vdev(zhp, path, &avail_spare, &l2cache)) == NULL)
1344 		return (zfs_error(hdl, EZFS_NODEVICE, msg));
1345 
1346 	verify(nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_GUID, &zc.zc_guid) == 0);
1347 
1348 	if (avail_spare ||
1349 	    is_guid_type(zhp, zc.zc_guid, ZPOOL_CONFIG_SPARES) == B_TRUE)
1350 		return (zfs_error(hdl, EZFS_ISSPARE, msg));
1351 
1352 	zc.zc_cookie = VDEV_STATE_ONLINE;
1353 	zc.zc_obj = flags;
1354 
1355 	if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_VDEV_SET_STATE, &zc) != 0)
1356 		return (zpool_standard_error(hdl, errno, msg));
1357 
1358 	*newstate = zc.zc_cookie;
1359 	return (0);
1360 }
1361 
1362 /*
1363  * Take the specified vdev offline
1364  */
1365 int
1366 zpool_vdev_offline(zpool_handle_t *zhp, const char *path, boolean_t istmp)
1367 {
1368 	zfs_cmd_t zc = { 0 };
1369 	char msg[1024];
1370 	nvlist_t *tgt;
1371 	boolean_t avail_spare, l2cache;
1372 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1373 
1374 	(void) snprintf(msg, sizeof (msg),
1375 	    dgettext(TEXT_DOMAIN, "cannot offline %s"), path);
1376 
1377 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1378 	if ((tgt = zpool_find_vdev(zhp, path, &avail_spare, &l2cache)) == NULL)
1379 		return (zfs_error(hdl, EZFS_NODEVICE, msg));
1380 
1381 	verify(nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_GUID, &zc.zc_guid) == 0);
1382 
1383 	if (avail_spare ||
1384 	    is_guid_type(zhp, zc.zc_guid, ZPOOL_CONFIG_SPARES) == B_TRUE)
1385 		return (zfs_error(hdl, EZFS_ISSPARE, msg));
1386 
1387 	zc.zc_cookie = VDEV_STATE_OFFLINE;
1388 	zc.zc_obj = istmp ? ZFS_OFFLINE_TEMPORARY : 0;
1389 
1390 	if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_VDEV_SET_STATE, &zc) == 0)
1391 		return (0);
1392 
1393 	switch (errno) {
1394 	case EBUSY:
1395 
1396 		/*
1397 		 * There are no other replicas of this device.
1398 		 */
1399 		return (zfs_error(hdl, EZFS_NOREPLICAS, msg));
1400 
1401 	default:
1402 		return (zpool_standard_error(hdl, errno, msg));
1403 	}
1404 }
1405 
1406 /*
1407  * Mark the given vdev faulted.
1408  */
1409 int
1410 zpool_vdev_fault(zpool_handle_t *zhp, uint64_t guid)
1411 {
1412 	zfs_cmd_t zc = { 0 };
1413 	char msg[1024];
1414 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1415 
1416 	(void) snprintf(msg, sizeof (msg),
1417 	    dgettext(TEXT_DOMAIN, "cannot fault %llu"), guid);
1418 
1419 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1420 	zc.zc_guid = guid;
1421 	zc.zc_cookie = VDEV_STATE_FAULTED;
1422 
1423 	if (ioctl(zhp->zpool_hdl->libzfs_fd, ZFS_IOC_VDEV_SET_STATE, &zc) == 0)
1424 		return (0);
1425 
1426 	switch (errno) {
1427 	case EBUSY:
1428 
1429 		/*
1430 		 * There are no other replicas of this device.
1431 		 */
1432 		return (zfs_error(hdl, EZFS_NOREPLICAS, msg));
1433 
1434 	default:
1435 		return (zpool_standard_error(hdl, errno, msg));
1436 	}
1437 
1438 }
1439 
1440 /*
1441  * Mark the given vdev degraded.
1442  */
1443 int
1444 zpool_vdev_degrade(zpool_handle_t *zhp, uint64_t guid)
1445 {
1446 	zfs_cmd_t zc = { 0 };
1447 	char msg[1024];
1448 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1449 
1450 	(void) snprintf(msg, sizeof (msg),
1451 	    dgettext(TEXT_DOMAIN, "cannot degrade %llu"), guid);
1452 
1453 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1454 	zc.zc_guid = guid;
1455 	zc.zc_cookie = VDEV_STATE_DEGRADED;
1456 
1457 	if (ioctl(zhp->zpool_hdl->libzfs_fd, ZFS_IOC_VDEV_SET_STATE, &zc) == 0)
1458 		return (0);
1459 
1460 	return (zpool_standard_error(hdl, errno, msg));
1461 }
1462 
1463 /*
1464  * Returns TRUE if the given nvlist is a vdev that was originally swapped in as
1465  * a hot spare.
1466  */
1467 static boolean_t
1468 is_replacing_spare(nvlist_t *search, nvlist_t *tgt, int which)
1469 {
1470 	nvlist_t **child;
1471 	uint_t c, children;
1472 	char *type;
1473 
1474 	if (nvlist_lookup_nvlist_array(search, ZPOOL_CONFIG_CHILDREN, &child,
1475 	    &children) == 0) {
1476 		verify(nvlist_lookup_string(search, ZPOOL_CONFIG_TYPE,
1477 		    &type) == 0);
1478 
1479 		if (strcmp(type, VDEV_TYPE_SPARE) == 0 &&
1480 		    children == 2 && child[which] == tgt)
1481 			return (B_TRUE);
1482 
1483 		for (c = 0; c < children; c++)
1484 			if (is_replacing_spare(child[c], tgt, which))
1485 				return (B_TRUE);
1486 	}
1487 
1488 	return (B_FALSE);
1489 }
1490 
1491 /*
1492  * Attach new_disk (fully described by nvroot) to old_disk.
1493  * If 'replacing' is specified, the new disk will replace the old one.
1494  */
1495 int
1496 zpool_vdev_attach(zpool_handle_t *zhp,
1497     const char *old_disk, const char *new_disk, nvlist_t *nvroot, int replacing)
1498 {
1499 	zfs_cmd_t zc = { 0 };
1500 	char msg[1024];
1501 	int ret;
1502 	nvlist_t *tgt;
1503 	boolean_t avail_spare, l2cache;
1504 	uint64_t val, is_log;
1505 	char *path;
1506 	nvlist_t **child;
1507 	uint_t children;
1508 	nvlist_t *config_root;
1509 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1510 
1511 	if (replacing)
1512 		(void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN,
1513 		    "cannot replace %s with %s"), old_disk, new_disk);
1514 	else
1515 		(void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN,
1516 		    "cannot attach %s to %s"), new_disk, old_disk);
1517 
1518 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1519 	if ((tgt = zpool_find_vdev(zhp, old_disk, &avail_spare, &l2cache)) == 0)
1520 		return (zfs_error(hdl, EZFS_NODEVICE, msg));
1521 
1522 	if (avail_spare)
1523 		return (zfs_error(hdl, EZFS_ISSPARE, msg));
1524 
1525 	if (l2cache)
1526 		return (zfs_error(hdl, EZFS_ISL2CACHE, msg));
1527 
1528 	verify(nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_GUID, &zc.zc_guid) == 0);
1529 	zc.zc_cookie = replacing;
1530 
1531 	if (nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_CHILDREN,
1532 	    &child, &children) != 0 || children != 1) {
1533 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1534 		    "new device must be a single disk"));
1535 		return (zfs_error(hdl, EZFS_INVALCONFIG, msg));
1536 	}
1537 
1538 	verify(nvlist_lookup_nvlist(zpool_get_config(zhp, NULL),
1539 	    ZPOOL_CONFIG_VDEV_TREE, &config_root) == 0);
1540 
1541 	/*
1542 	 * If the target is a hot spare that has been swapped in, we can only
1543 	 * replace it with another hot spare.
1544 	 */
1545 	if (replacing &&
1546 	    nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_IS_SPARE, &val) == 0 &&
1547 	    nvlist_lookup_string(child[0], ZPOOL_CONFIG_PATH, &path) == 0 &&
1548 	    (zpool_find_vdev(zhp, path, &avail_spare, &l2cache) == NULL ||
1549 	    !avail_spare) && is_replacing_spare(config_root, tgt, 1)) {
1550 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1551 		    "can only be replaced by another hot spare"));
1552 		return (zfs_error(hdl, EZFS_BADTARGET, msg));
1553 	}
1554 
1555 	/*
1556 	 * If we are attempting to replace a spare, it canot be applied to an
1557 	 * already spared device.
1558 	 */
1559 	if (replacing &&
1560 	    nvlist_lookup_string(child[0], ZPOOL_CONFIG_PATH, &path) == 0 &&
1561 	    zpool_find_vdev(zhp, path, &avail_spare, &l2cache) != NULL &&
1562 	    avail_spare && is_replacing_spare(config_root, tgt, 0)) {
1563 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1564 		    "device has already been replaced with a spare"));
1565 		return (zfs_error(hdl, EZFS_BADTARGET, msg));
1566 	}
1567 
1568 	if (zcmd_write_conf_nvlist(hdl, &zc, nvroot) != 0)
1569 		return (-1);
1570 
1571 	ret = zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_VDEV_ATTACH, &zc);
1572 
1573 	zcmd_free_nvlists(&zc);
1574 
1575 	if (ret == 0)
1576 		return (0);
1577 
1578 	switch (errno) {
1579 	case ENOTSUP:
1580 		/*
1581 		 * Can't attach to or replace this type of vdev.
1582 		 */
1583 		if (replacing) {
1584 			is_log = B_FALSE;
1585 			(void) nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_IS_LOG,
1586 			    &is_log);
1587 			if (is_log)
1588 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1589 				    "cannot replace a log with a spare"));
1590 			else
1591 				zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1592 				    "cannot replace a replacing device"));
1593 		} else {
1594 			zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1595 			    "can only attach to mirrors and top-level "
1596 			    "disks"));
1597 		}
1598 		(void) zfs_error(hdl, EZFS_BADTARGET, msg);
1599 		break;
1600 
1601 	case EINVAL:
1602 		/*
1603 		 * The new device must be a single disk.
1604 		 */
1605 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1606 		    "new device must be a single disk"));
1607 		(void) zfs_error(hdl, EZFS_INVALCONFIG, msg);
1608 		break;
1609 
1610 	case EBUSY:
1611 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "%s is busy"),
1612 		    new_disk);
1613 		(void) zfs_error(hdl, EZFS_BADDEV, msg);
1614 		break;
1615 
1616 	case EOVERFLOW:
1617 		/*
1618 		 * The new device is too small.
1619 		 */
1620 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1621 		    "device is too small"));
1622 		(void) zfs_error(hdl, EZFS_BADDEV, msg);
1623 		break;
1624 
1625 	case EDOM:
1626 		/*
1627 		 * The new device has a different alignment requirement.
1628 		 */
1629 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1630 		    "devices have different sector alignment"));
1631 		(void) zfs_error(hdl, EZFS_BADDEV, msg);
1632 		break;
1633 
1634 	case ENAMETOOLONG:
1635 		/*
1636 		 * The resulting top-level vdev spec won't fit in the label.
1637 		 */
1638 		(void) zfs_error(hdl, EZFS_DEVOVERFLOW, msg);
1639 		break;
1640 
1641 	default:
1642 		(void) zpool_standard_error(hdl, errno, msg);
1643 	}
1644 
1645 	return (-1);
1646 }
1647 
1648 /*
1649  * Detach the specified device.
1650  */
1651 int
1652 zpool_vdev_detach(zpool_handle_t *zhp, const char *path)
1653 {
1654 	zfs_cmd_t zc = { 0 };
1655 	char msg[1024];
1656 	nvlist_t *tgt;
1657 	boolean_t avail_spare, l2cache;
1658 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1659 
1660 	(void) snprintf(msg, sizeof (msg),
1661 	    dgettext(TEXT_DOMAIN, "cannot detach %s"), path);
1662 
1663 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1664 	if ((tgt = zpool_find_vdev(zhp, path, &avail_spare, &l2cache)) == 0)
1665 		return (zfs_error(hdl, EZFS_NODEVICE, msg));
1666 
1667 	if (avail_spare)
1668 		return (zfs_error(hdl, EZFS_ISSPARE, msg));
1669 
1670 	if (l2cache)
1671 		return (zfs_error(hdl, EZFS_ISL2CACHE, msg));
1672 
1673 	verify(nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_GUID, &zc.zc_guid) == 0);
1674 
1675 	if (zfs_ioctl(hdl, ZFS_IOC_VDEV_DETACH, &zc) == 0)
1676 		return (0);
1677 
1678 	switch (errno) {
1679 
1680 	case ENOTSUP:
1681 		/*
1682 		 * Can't detach from this type of vdev.
1683 		 */
1684 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "only "
1685 		    "applicable to mirror and replacing vdevs"));
1686 		(void) zfs_error(zhp->zpool_hdl, EZFS_BADTARGET, msg);
1687 		break;
1688 
1689 	case EBUSY:
1690 		/*
1691 		 * There are no other replicas of this device.
1692 		 */
1693 		(void) zfs_error(hdl, EZFS_NOREPLICAS, msg);
1694 		break;
1695 
1696 	default:
1697 		(void) zpool_standard_error(hdl, errno, msg);
1698 	}
1699 
1700 	return (-1);
1701 }
1702 
1703 /*
1704  * Remove the given device.  Currently, this is supported only for hot spares
1705  * and level 2 cache devices.
1706  */
1707 int
1708 zpool_vdev_remove(zpool_handle_t *zhp, const char *path)
1709 {
1710 	zfs_cmd_t zc = { 0 };
1711 	char msg[1024];
1712 	nvlist_t *tgt;
1713 	boolean_t avail_spare, l2cache;
1714 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1715 
1716 	(void) snprintf(msg, sizeof (msg),
1717 	    dgettext(TEXT_DOMAIN, "cannot remove %s"), path);
1718 
1719 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1720 	if ((tgt = zpool_find_vdev(zhp, path, &avail_spare, &l2cache)) == 0)
1721 		return (zfs_error(hdl, EZFS_NODEVICE, msg));
1722 
1723 	if (!avail_spare && !l2cache) {
1724 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
1725 		    "only inactive hot spares or cache devices "
1726 		    "can be removed"));
1727 		return (zfs_error(hdl, EZFS_NODEVICE, msg));
1728 	}
1729 
1730 	verify(nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_GUID, &zc.zc_guid) == 0);
1731 
1732 	if (zfs_ioctl(hdl, ZFS_IOC_VDEV_REMOVE, &zc) == 0)
1733 		return (0);
1734 
1735 	return (zpool_standard_error(hdl, errno, msg));
1736 }
1737 
1738 /*
1739  * Clear the errors for the pool, or the particular device if specified.
1740  */
1741 int
1742 zpool_clear(zpool_handle_t *zhp, const char *path)
1743 {
1744 	zfs_cmd_t zc = { 0 };
1745 	char msg[1024];
1746 	nvlist_t *tgt;
1747 	boolean_t avail_spare, l2cache;
1748 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1749 
1750 	if (path)
1751 		(void) snprintf(msg, sizeof (msg),
1752 		    dgettext(TEXT_DOMAIN, "cannot clear errors for %s"),
1753 		    path);
1754 	else
1755 		(void) snprintf(msg, sizeof (msg),
1756 		    dgettext(TEXT_DOMAIN, "cannot clear errors for %s"),
1757 		    zhp->zpool_name);
1758 
1759 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1760 	if (path) {
1761 		if ((tgt = zpool_find_vdev(zhp, path, &avail_spare,
1762 		    &l2cache)) == 0)
1763 			return (zfs_error(hdl, EZFS_NODEVICE, msg));
1764 
1765 		/*
1766 		 * Don't allow error clearing for hot spares.  Do allow
1767 		 * error clearing for l2cache devices.
1768 		 */
1769 		if (avail_spare)
1770 			return (zfs_error(hdl, EZFS_ISSPARE, msg));
1771 
1772 		verify(nvlist_lookup_uint64(tgt, ZPOOL_CONFIG_GUID,
1773 		    &zc.zc_guid) == 0);
1774 	}
1775 
1776 	if (zfs_ioctl(hdl, ZFS_IOC_CLEAR, &zc) == 0)
1777 		return (0);
1778 
1779 	return (zpool_standard_error(hdl, errno, msg));
1780 }
1781 
1782 /*
1783  * Similar to zpool_clear(), but takes a GUID (used by fmd).
1784  */
1785 int
1786 zpool_vdev_clear(zpool_handle_t *zhp, uint64_t guid)
1787 {
1788 	zfs_cmd_t zc = { 0 };
1789 	char msg[1024];
1790 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1791 
1792 	(void) snprintf(msg, sizeof (msg),
1793 	    dgettext(TEXT_DOMAIN, "cannot clear errors for %llx"),
1794 	    guid);
1795 
1796 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
1797 	zc.zc_guid = guid;
1798 
1799 	if (ioctl(hdl->libzfs_fd, ZFS_IOC_CLEAR, &zc) == 0)
1800 		return (0);
1801 
1802 	return (zpool_standard_error(hdl, errno, msg));
1803 }
1804 
1805 /*
1806  * Iterate over all zvols in a given pool by walking the /dev/zvol/dsk/<pool>
1807  * hierarchy.
1808  */
1809 int
1810 zpool_iter_zvol(zpool_handle_t *zhp, int (*cb)(const char *, void *),
1811     void *data)
1812 {
1813 	libzfs_handle_t *hdl = zhp->zpool_hdl;
1814 	char (*paths)[MAXPATHLEN];
1815 	size_t size = 4;
1816 	int curr, fd, base, ret = 0;
1817 	DIR *dirp;
1818 	struct dirent *dp;
1819 	struct stat st;
1820 
1821 	if ((base = open("/dev/zvol/dsk", O_RDONLY)) < 0)
1822 		return (errno == ENOENT ? 0 : -1);
1823 
1824 	if (fstatat(base, zhp->zpool_name, &st, 0) != 0) {
1825 		int err = errno;
1826 		(void) close(base);
1827 		return (err == ENOENT ? 0 : -1);
1828 	}
1829 
1830 	/*
1831 	 * Oddly this wasn't a directory -- ignore that failure since we
1832 	 * know there are no links lower in the (non-existant) hierarchy.
1833 	 */
1834 	if (!S_ISDIR(st.st_mode)) {
1835 		(void) close(base);
1836 		return (0);
1837 	}
1838 
1839 	if ((paths = zfs_alloc(hdl, size * sizeof (paths[0]))) == NULL) {
1840 		(void) close(base);
1841 		return (-1);
1842 	}
1843 
1844 	(void) strlcpy(paths[0], zhp->zpool_name, sizeof (paths[0]));
1845 	curr = 0;
1846 
1847 	while (curr >= 0) {
1848 		if (fstatat(base, paths[curr], &st, AT_SYMLINK_NOFOLLOW) != 0)
1849 			goto err;
1850 
1851 		if (S_ISDIR(st.st_mode)) {
1852 			if ((fd = openat(base, paths[curr], O_RDONLY)) < 0)
1853 				goto err;
1854 
1855 			if ((dirp = fdopendir(fd)) == NULL) {
1856 				(void) close(fd);
1857 				goto err;
1858 			}
1859 
1860 			while ((dp = readdir(dirp)) != NULL) {
1861 				if (dp->d_name[0] == '.')
1862 					continue;
1863 
1864 				if (curr + 1 == size) {
1865 					paths = zfs_realloc(hdl, paths,
1866 					    size * sizeof (paths[0]),
1867 					    size * 2 * sizeof (paths[0]));
1868 					if (paths == NULL) {
1869 						(void) closedir(dirp);
1870 						(void) close(fd);
1871 						goto err;
1872 					}
1873 
1874 					size *= 2;
1875 				}
1876 
1877 				(void) strlcpy(paths[curr + 1], paths[curr],
1878 				    sizeof (paths[curr + 1]));
1879 				(void) strlcat(paths[curr], "/",
1880 				    sizeof (paths[curr]));
1881 				(void) strlcat(paths[curr], dp->d_name,
1882 				    sizeof (paths[curr]));
1883 				curr++;
1884 			}
1885 
1886 			(void) closedir(dirp);
1887 
1888 		} else {
1889 			if ((ret = cb(paths[curr], data)) != 0)
1890 				break;
1891 		}
1892 
1893 		curr--;
1894 	}
1895 
1896 	free(paths);
1897 	(void) close(base);
1898 
1899 	return (ret);
1900 
1901 err:
1902 	free(paths);
1903 	(void) close(base);
1904 	return (-1);
1905 }
1906 
1907 typedef struct zvol_cb {
1908 	zpool_handle_t *zcb_pool;
1909 	boolean_t zcb_create;
1910 } zvol_cb_t;
1911 
1912 /*ARGSUSED*/
1913 static int
1914 do_zvol_create(zfs_handle_t *zhp, void *data)
1915 {
1916 	int ret = 0;
1917 
1918 	if (ZFS_IS_VOLUME(zhp)) {
1919 		(void) zvol_create_link(zhp->zfs_hdl, zhp->zfs_name);
1920 		ret = zfs_iter_snapshots(zhp, do_zvol_create, NULL);
1921 	}
1922 
1923 	if (ret == 0)
1924 		ret = zfs_iter_filesystems(zhp, do_zvol_create, NULL);
1925 
1926 	zfs_close(zhp);
1927 
1928 	return (ret);
1929 }
1930 
1931 /*
1932  * Iterate over all zvols in the pool and make any necessary minor nodes.
1933  */
1934 int
1935 zpool_create_zvol_links(zpool_handle_t *zhp)
1936 {
1937 	zfs_handle_t *zfp;
1938 	int ret;
1939 
1940 	/*
1941 	 * If the pool is unavailable, just return success.
1942 	 */
1943 	if ((zfp = make_dataset_handle(zhp->zpool_hdl,
1944 	    zhp->zpool_name)) == NULL)
1945 		return (0);
1946 
1947 	ret = zfs_iter_filesystems(zfp, do_zvol_create, NULL);
1948 
1949 	zfs_close(zfp);
1950 	return (ret);
1951 }
1952 
1953 static int
1954 do_zvol_remove(const char *dataset, void *data)
1955 {
1956 	zpool_handle_t *zhp = data;
1957 
1958 	return (zvol_remove_link(zhp->zpool_hdl, dataset));
1959 }
1960 
1961 /*
1962  * Iterate over all zvols in the pool and remove any minor nodes.  We iterate
1963  * by examining the /dev links so that a corrupted pool doesn't impede this
1964  * operation.
1965  */
1966 int
1967 zpool_remove_zvol_links(zpool_handle_t *zhp)
1968 {
1969 	return (zpool_iter_zvol(zhp, do_zvol_remove, zhp));
1970 }
1971 
1972 /*
1973  * Convert from a devid string to a path.
1974  */
1975 static char *
1976 devid_to_path(char *devid_str)
1977 {
1978 	ddi_devid_t devid;
1979 	char *minor;
1980 	char *path;
1981 	devid_nmlist_t *list = NULL;
1982 	int ret;
1983 
1984 	if (devid_str_decode(devid_str, &devid, &minor) != 0)
1985 		return (NULL);
1986 
1987 	ret = devid_deviceid_to_nmlist("/dev", devid, minor, &list);
1988 
1989 	devid_str_free(minor);
1990 	devid_free(devid);
1991 
1992 	if (ret != 0)
1993 		return (NULL);
1994 
1995 	if ((path = strdup(list[0].devname)) == NULL)
1996 		return (NULL);
1997 
1998 	devid_free_nmlist(list);
1999 
2000 	return (path);
2001 }
2002 
2003 /*
2004  * Convert from a path to a devid string.
2005  */
2006 static char *
2007 path_to_devid(const char *path)
2008 {
2009 	int fd;
2010 	ddi_devid_t devid;
2011 	char *minor, *ret;
2012 
2013 	if ((fd = open(path, O_RDONLY)) < 0)
2014 		return (NULL);
2015 
2016 	minor = NULL;
2017 	ret = NULL;
2018 	if (devid_get(fd, &devid) == 0) {
2019 		if (devid_get_minor_name(fd, &minor) == 0)
2020 			ret = devid_str_encode(devid, minor);
2021 		if (minor != NULL)
2022 			devid_str_free(minor);
2023 		devid_free(devid);
2024 	}
2025 	(void) close(fd);
2026 
2027 	return (ret);
2028 }
2029 
2030 /*
2031  * Issue the necessary ioctl() to update the stored path value for the vdev.  We
2032  * ignore any failure here, since a common case is for an unprivileged user to
2033  * type 'zpool status', and we'll display the correct information anyway.
2034  */
2035 static void
2036 set_path(zpool_handle_t *zhp, nvlist_t *nv, const char *path)
2037 {
2038 	zfs_cmd_t zc = { 0 };
2039 
2040 	(void) strncpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
2041 	(void) strncpy(zc.zc_value, path, sizeof (zc.zc_value));
2042 	verify(nvlist_lookup_uint64(nv, ZPOOL_CONFIG_GUID,
2043 	    &zc.zc_guid) == 0);
2044 
2045 	(void) ioctl(zhp->zpool_hdl->libzfs_fd, ZFS_IOC_VDEV_SETPATH, &zc);
2046 }
2047 
2048 /*
2049  * Given a vdev, return the name to display in iostat.  If the vdev has a path,
2050  * we use that, stripping off any leading "/dev/dsk/"; if not, we use the type.
2051  * We also check if this is a whole disk, in which case we strip off the
2052  * trailing 's0' slice name.
2053  *
2054  * This routine is also responsible for identifying when disks have been
2055  * reconfigured in a new location.  The kernel will have opened the device by
2056  * devid, but the path will still refer to the old location.  To catch this, we
2057  * first do a path -> devid translation (which is fast for the common case).  If
2058  * the devid matches, we're done.  If not, we do a reverse devid -> path
2059  * translation and issue the appropriate ioctl() to update the path of the vdev.
2060  * If 'zhp' is NULL, then this is an exported pool, and we don't need to do any
2061  * of these checks.
2062  */
2063 char *
2064 zpool_vdev_name(libzfs_handle_t *hdl, zpool_handle_t *zhp, nvlist_t *nv)
2065 {
2066 	char *path, *devid;
2067 	uint64_t value;
2068 	char buf[64];
2069 	vdev_stat_t *vs;
2070 	uint_t vsc;
2071 
2072 	if (nvlist_lookup_uint64(nv, ZPOOL_CONFIG_NOT_PRESENT,
2073 	    &value) == 0) {
2074 		verify(nvlist_lookup_uint64(nv, ZPOOL_CONFIG_GUID,
2075 		    &value) == 0);
2076 		(void) snprintf(buf, sizeof (buf), "%llu",
2077 		    (u_longlong_t)value);
2078 		path = buf;
2079 	} else if (nvlist_lookup_string(nv, ZPOOL_CONFIG_PATH, &path) == 0) {
2080 
2081 		/*
2082 		 * If the device is dead (faulted, offline, etc) then don't
2083 		 * bother opening it.  Otherwise we may be forcing the user to
2084 		 * open a misbehaving device, which can have undesirable
2085 		 * effects.
2086 		 */
2087 		if ((nvlist_lookup_uint64_array(nv, ZPOOL_CONFIG_STATS,
2088 		    (uint64_t **)&vs, &vsc) != 0 ||
2089 		    vs->vs_state >= VDEV_STATE_DEGRADED) &&
2090 		    zhp != NULL &&
2091 		    nvlist_lookup_string(nv, ZPOOL_CONFIG_DEVID, &devid) == 0) {
2092 			/*
2093 			 * Determine if the current path is correct.
2094 			 */
2095 			char *newdevid = path_to_devid(path);
2096 
2097 			if (newdevid == NULL ||
2098 			    strcmp(devid, newdevid) != 0) {
2099 				char *newpath;
2100 
2101 				if ((newpath = devid_to_path(devid)) != NULL) {
2102 					/*
2103 					 * Update the path appropriately.
2104 					 */
2105 					set_path(zhp, nv, newpath);
2106 					if (nvlist_add_string(nv,
2107 					    ZPOOL_CONFIG_PATH, newpath) == 0)
2108 						verify(nvlist_lookup_string(nv,
2109 						    ZPOOL_CONFIG_PATH,
2110 						    &path) == 0);
2111 					free(newpath);
2112 				}
2113 			}
2114 
2115 			if (newdevid)
2116 				devid_str_free(newdevid);
2117 		}
2118 
2119 		if (strncmp(path, "/dev/dsk/", 9) == 0)
2120 			path += 9;
2121 
2122 		if (nvlist_lookup_uint64(nv, ZPOOL_CONFIG_WHOLE_DISK,
2123 		    &value) == 0 && value) {
2124 			char *tmp = zfs_strdup(hdl, path);
2125 			if (tmp == NULL)
2126 				return (NULL);
2127 			tmp[strlen(path) - 2] = '\0';
2128 			return (tmp);
2129 		}
2130 	} else {
2131 		verify(nvlist_lookup_string(nv, ZPOOL_CONFIG_TYPE, &path) == 0);
2132 
2133 		/*
2134 		 * If it's a raidz device, we need to stick in the parity level.
2135 		 */
2136 		if (strcmp(path, VDEV_TYPE_RAIDZ) == 0) {
2137 			verify(nvlist_lookup_uint64(nv, ZPOOL_CONFIG_NPARITY,
2138 			    &value) == 0);
2139 			(void) snprintf(buf, sizeof (buf), "%s%llu", path,
2140 			    (u_longlong_t)value);
2141 			path = buf;
2142 		}
2143 	}
2144 
2145 	return (zfs_strdup(hdl, path));
2146 }
2147 
2148 static int
2149 zbookmark_compare(const void *a, const void *b)
2150 {
2151 	return (memcmp(a, b, sizeof (zbookmark_t)));
2152 }
2153 
2154 /*
2155  * Retrieve the persistent error log, uniquify the members, and return to the
2156  * caller.
2157  */
2158 int
2159 zpool_get_errlog(zpool_handle_t *zhp, nvlist_t **nverrlistp)
2160 {
2161 	zfs_cmd_t zc = { 0 };
2162 	uint64_t count;
2163 	zbookmark_t *zb = NULL;
2164 	int i;
2165 
2166 	/*
2167 	 * Retrieve the raw error list from the kernel.  If the number of errors
2168 	 * has increased, allocate more space and continue until we get the
2169 	 * entire list.
2170 	 */
2171 	verify(nvlist_lookup_uint64(zhp->zpool_config, ZPOOL_CONFIG_ERRCOUNT,
2172 	    &count) == 0);
2173 	if (count == 0)
2174 		return (0);
2175 	if ((zc.zc_nvlist_dst = (uintptr_t)zfs_alloc(zhp->zpool_hdl,
2176 	    count * sizeof (zbookmark_t))) == (uintptr_t)NULL)
2177 		return (-1);
2178 	zc.zc_nvlist_dst_size = count;
2179 	(void) strcpy(zc.zc_name, zhp->zpool_name);
2180 	for (;;) {
2181 		if (ioctl(zhp->zpool_hdl->libzfs_fd, ZFS_IOC_ERROR_LOG,
2182 		    &zc) != 0) {
2183 			free((void *)(uintptr_t)zc.zc_nvlist_dst);
2184 			if (errno == ENOMEM) {
2185 				count = zc.zc_nvlist_dst_size;
2186 				if ((zc.zc_nvlist_dst = (uintptr_t)
2187 				    zfs_alloc(zhp->zpool_hdl, count *
2188 				    sizeof (zbookmark_t))) == (uintptr_t)NULL)
2189 					return (-1);
2190 			} else {
2191 				return (-1);
2192 			}
2193 		} else {
2194 			break;
2195 		}
2196 	}
2197 
2198 	/*
2199 	 * Sort the resulting bookmarks.  This is a little confusing due to the
2200 	 * implementation of ZFS_IOC_ERROR_LOG.  The bookmarks are copied last
2201 	 * to first, and 'zc_nvlist_dst_size' indicates the number of boomarks
2202 	 * _not_ copied as part of the process.  So we point the start of our
2203 	 * array appropriate and decrement the total number of elements.
2204 	 */
2205 	zb = ((zbookmark_t *)(uintptr_t)zc.zc_nvlist_dst) +
2206 	    zc.zc_nvlist_dst_size;
2207 	count -= zc.zc_nvlist_dst_size;
2208 
2209 	qsort(zb, count, sizeof (zbookmark_t), zbookmark_compare);
2210 
2211 	verify(nvlist_alloc(nverrlistp, 0, KM_SLEEP) == 0);
2212 
2213 	/*
2214 	 * Fill in the nverrlistp with nvlist's of dataset and object numbers.
2215 	 */
2216 	for (i = 0; i < count; i++) {
2217 		nvlist_t *nv;
2218 
2219 		/* ignoring zb_blkid and zb_level for now */
2220 		if (i > 0 && zb[i-1].zb_objset == zb[i].zb_objset &&
2221 		    zb[i-1].zb_object == zb[i].zb_object)
2222 			continue;
2223 
2224 		if (nvlist_alloc(&nv, NV_UNIQUE_NAME, KM_SLEEP) != 0)
2225 			goto nomem;
2226 		if (nvlist_add_uint64(nv, ZPOOL_ERR_DATASET,
2227 		    zb[i].zb_objset) != 0) {
2228 			nvlist_free(nv);
2229 			goto nomem;
2230 		}
2231 		if (nvlist_add_uint64(nv, ZPOOL_ERR_OBJECT,
2232 		    zb[i].zb_object) != 0) {
2233 			nvlist_free(nv);
2234 			goto nomem;
2235 		}
2236 		if (nvlist_add_nvlist(*nverrlistp, "ejk", nv) != 0) {
2237 			nvlist_free(nv);
2238 			goto nomem;
2239 		}
2240 		nvlist_free(nv);
2241 	}
2242 
2243 	free((void *)(uintptr_t)zc.zc_nvlist_dst);
2244 	return (0);
2245 
2246 nomem:
2247 	free((void *)(uintptr_t)zc.zc_nvlist_dst);
2248 	return (no_memory(zhp->zpool_hdl));
2249 }
2250 
2251 /*
2252  * Upgrade a ZFS pool to the latest on-disk version.
2253  */
2254 int
2255 zpool_upgrade(zpool_handle_t *zhp, uint64_t new_version)
2256 {
2257 	zfs_cmd_t zc = { 0 };
2258 	libzfs_handle_t *hdl = zhp->zpool_hdl;
2259 
2260 	(void) strcpy(zc.zc_name, zhp->zpool_name);
2261 	zc.zc_cookie = new_version;
2262 
2263 	if (zfs_ioctl(hdl, ZFS_IOC_POOL_UPGRADE, &zc) != 0)
2264 		return (zpool_standard_error_fmt(hdl, errno,
2265 		    dgettext(TEXT_DOMAIN, "cannot upgrade '%s'"),
2266 		    zhp->zpool_name));
2267 	return (0);
2268 }
2269 
2270 void
2271 zpool_set_history_str(const char *subcommand, int argc, char **argv,
2272     char *history_str)
2273 {
2274 	int i;
2275 
2276 	(void) strlcpy(history_str, subcommand, HIS_MAX_RECORD_LEN);
2277 	for (i = 1; i < argc; i++) {
2278 		if (strlen(history_str) + 1 + strlen(argv[i]) >
2279 		    HIS_MAX_RECORD_LEN)
2280 			break;
2281 		(void) strlcat(history_str, " ", HIS_MAX_RECORD_LEN);
2282 		(void) strlcat(history_str, argv[i], HIS_MAX_RECORD_LEN);
2283 	}
2284 }
2285 
2286 /*
2287  * Stage command history for logging.
2288  */
2289 int
2290 zpool_stage_history(libzfs_handle_t *hdl, const char *history_str)
2291 {
2292 	if (history_str == NULL)
2293 		return (EINVAL);
2294 
2295 	if (strlen(history_str) > HIS_MAX_RECORD_LEN)
2296 		return (EINVAL);
2297 
2298 	if (hdl->libzfs_log_str != NULL)
2299 		free(hdl->libzfs_log_str);
2300 
2301 	if ((hdl->libzfs_log_str = strdup(history_str)) == NULL)
2302 		return (no_memory(hdl));
2303 
2304 	return (0);
2305 }
2306 
2307 /*
2308  * Perform ioctl to get some command history of a pool.
2309  *
2310  * 'buf' is the buffer to fill up to 'len' bytes.  'off' is the
2311  * logical offset of the history buffer to start reading from.
2312  *
2313  * Upon return, 'off' is the next logical offset to read from and
2314  * 'len' is the actual amount of bytes read into 'buf'.
2315  */
2316 static int
2317 get_history(zpool_handle_t *zhp, char *buf, uint64_t *off, uint64_t *len)
2318 {
2319 	zfs_cmd_t zc = { 0 };
2320 	libzfs_handle_t *hdl = zhp->zpool_hdl;
2321 
2322 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
2323 
2324 	zc.zc_history = (uint64_t)(uintptr_t)buf;
2325 	zc.zc_history_len = *len;
2326 	zc.zc_history_offset = *off;
2327 
2328 	if (ioctl(hdl->libzfs_fd, ZFS_IOC_POOL_GET_HISTORY, &zc) != 0) {
2329 		switch (errno) {
2330 		case EPERM:
2331 			return (zfs_error_fmt(hdl, EZFS_PERM,
2332 			    dgettext(TEXT_DOMAIN,
2333 			    "cannot show history for pool '%s'"),
2334 			    zhp->zpool_name));
2335 		case ENOENT:
2336 			return (zfs_error_fmt(hdl, EZFS_NOHISTORY,
2337 			    dgettext(TEXT_DOMAIN, "cannot get history for pool "
2338 			    "'%s'"), zhp->zpool_name));
2339 		case ENOTSUP:
2340 			return (zfs_error_fmt(hdl, EZFS_BADVERSION,
2341 			    dgettext(TEXT_DOMAIN, "cannot get history for pool "
2342 			    "'%s', pool must be upgraded"), zhp->zpool_name));
2343 		default:
2344 			return (zpool_standard_error_fmt(hdl, errno,
2345 			    dgettext(TEXT_DOMAIN,
2346 			    "cannot get history for '%s'"), zhp->zpool_name));
2347 		}
2348 	}
2349 
2350 	*len = zc.zc_history_len;
2351 	*off = zc.zc_history_offset;
2352 
2353 	return (0);
2354 }
2355 
2356 /*
2357  * Process the buffer of nvlists, unpacking and storing each nvlist record
2358  * into 'records'.  'leftover' is set to the number of bytes that weren't
2359  * processed as there wasn't a complete record.
2360  */
2361 static int
2362 zpool_history_unpack(char *buf, uint64_t bytes_read, uint64_t *leftover,
2363     nvlist_t ***records, uint_t *numrecords)
2364 {
2365 	uint64_t reclen;
2366 	nvlist_t *nv;
2367 	int i;
2368 
2369 	while (bytes_read > sizeof (reclen)) {
2370 
2371 		/* get length of packed record (stored as little endian) */
2372 		for (i = 0, reclen = 0; i < sizeof (reclen); i++)
2373 			reclen += (uint64_t)(((uchar_t *)buf)[i]) << (8*i);
2374 
2375 		if (bytes_read < sizeof (reclen) + reclen)
2376 			break;
2377 
2378 		/* unpack record */
2379 		if (nvlist_unpack(buf + sizeof (reclen), reclen, &nv, 0) != 0)
2380 			return (ENOMEM);
2381 		bytes_read -= sizeof (reclen) + reclen;
2382 		buf += sizeof (reclen) + reclen;
2383 
2384 		/* add record to nvlist array */
2385 		(*numrecords)++;
2386 		if (ISP2(*numrecords + 1)) {
2387 			*records = realloc(*records,
2388 			    *numrecords * 2 * sizeof (nvlist_t *));
2389 		}
2390 		(*records)[*numrecords - 1] = nv;
2391 	}
2392 
2393 	*leftover = bytes_read;
2394 	return (0);
2395 }
2396 
2397 #define	HIS_BUF_LEN	(128*1024)
2398 
2399 /*
2400  * Retrieve the command history of a pool.
2401  */
2402 int
2403 zpool_get_history(zpool_handle_t *zhp, nvlist_t **nvhisp)
2404 {
2405 	char buf[HIS_BUF_LEN];
2406 	uint64_t off = 0;
2407 	nvlist_t **records = NULL;
2408 	uint_t numrecords = 0;
2409 	int err, i;
2410 
2411 	do {
2412 		uint64_t bytes_read = sizeof (buf);
2413 		uint64_t leftover;
2414 
2415 		if ((err = get_history(zhp, buf, &off, &bytes_read)) != 0)
2416 			break;
2417 
2418 		/* if nothing else was read in, we're at EOF, just return */
2419 		if (!bytes_read)
2420 			break;
2421 
2422 		if ((err = zpool_history_unpack(buf, bytes_read,
2423 		    &leftover, &records, &numrecords)) != 0)
2424 			break;
2425 		off -= leftover;
2426 
2427 		/* CONSTCOND */
2428 	} while (1);
2429 
2430 	if (!err) {
2431 		verify(nvlist_alloc(nvhisp, NV_UNIQUE_NAME, 0) == 0);
2432 		verify(nvlist_add_nvlist_array(*nvhisp, ZPOOL_HIST_RECORD,
2433 		    records, numrecords) == 0);
2434 	}
2435 	for (i = 0; i < numrecords; i++)
2436 		nvlist_free(records[i]);
2437 	free(records);
2438 
2439 	return (err);
2440 }
2441 
2442 void
2443 zpool_obj_to_path(zpool_handle_t *zhp, uint64_t dsobj, uint64_t obj,
2444     char *pathname, size_t len)
2445 {
2446 	zfs_cmd_t zc = { 0 };
2447 	boolean_t mounted = B_FALSE;
2448 	char *mntpnt = NULL;
2449 	char dsname[MAXNAMELEN];
2450 
2451 	if (dsobj == 0) {
2452 		/* special case for the MOS */
2453 		(void) snprintf(pathname, len, "<metadata>:<0x%llx>", obj);
2454 		return;
2455 	}
2456 
2457 	/* get the dataset's name */
2458 	(void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name));
2459 	zc.zc_obj = dsobj;
2460 	if (ioctl(zhp->zpool_hdl->libzfs_fd,
2461 	    ZFS_IOC_DSOBJ_TO_DSNAME, &zc) != 0) {
2462 		/* just write out a path of two object numbers */
2463 		(void) snprintf(pathname, len, "<0x%llx>:<0x%llx>",
2464 		    dsobj, obj);
2465 		return;
2466 	}
2467 	(void) strlcpy(dsname, zc.zc_value, sizeof (dsname));
2468 
2469 	/* find out if the dataset is mounted */
2470 	mounted = is_mounted(zhp->zpool_hdl, dsname, &mntpnt);
2471 
2472 	/* get the corrupted object's path */
2473 	(void) strlcpy(zc.zc_name, dsname, sizeof (zc.zc_name));
2474 	zc.zc_obj = obj;
2475 	if (ioctl(zhp->zpool_hdl->libzfs_fd, ZFS_IOC_OBJ_TO_PATH,
2476 	    &zc) == 0) {
2477 		if (mounted) {
2478 			(void) snprintf(pathname, len, "%s%s", mntpnt,
2479 			    zc.zc_value);
2480 		} else {
2481 			(void) snprintf(pathname, len, "%s:%s",
2482 			    dsname, zc.zc_value);
2483 		}
2484 	} else {
2485 		(void) snprintf(pathname, len, "%s:<0x%llx>", dsname, obj);
2486 	}
2487 	free(mntpnt);
2488 }
2489 
2490 #define	RDISK_ROOT	"/dev/rdsk"
2491 #define	BACKUP_SLICE	"s2"
2492 /*
2493  * Don't start the slice at the default block of 34; many storage
2494  * devices will use a stripe width of 128k, so start there instead.
2495  */
2496 #define	NEW_START_BLOCK	256
2497 
2498 /*
2499  * determine where a partition starts on a disk in the current
2500  * configuration
2501  */
2502 static diskaddr_t
2503 find_start_block(nvlist_t *config)
2504 {
2505 	nvlist_t **child;
2506 	uint_t c, children;
2507 	char *path;
2508 	diskaddr_t sb = MAXOFFSET_T;
2509 	int fd;
2510 	char diskname[MAXPATHLEN];
2511 	uint64_t wholedisk;
2512 
2513 	if (nvlist_lookup_nvlist_array(config,
2514 	    ZPOOL_CONFIG_CHILDREN, &child, &children) != 0) {
2515 		if (nvlist_lookup_uint64(config,
2516 		    ZPOOL_CONFIG_WHOLE_DISK,
2517 		    &wholedisk) != 0 || !wholedisk) {
2518 			return (MAXOFFSET_T);
2519 		}
2520 		if (nvlist_lookup_string(config,
2521 		    ZPOOL_CONFIG_PATH, &path) != 0) {
2522 			return (MAXOFFSET_T);
2523 		}
2524 
2525 		(void) snprintf(diskname, sizeof (diskname), "%s%s",
2526 		    RDISK_ROOT, strrchr(path, '/'));
2527 		if ((fd = open(diskname, O_RDONLY|O_NDELAY)) >= 0) {
2528 			struct dk_gpt *vtoc;
2529 			if (efi_alloc_and_read(fd, &vtoc) >= 0) {
2530 				sb = vtoc->efi_parts[0].p_start;
2531 				efi_free(vtoc);
2532 			}
2533 			(void) close(fd);
2534 		}
2535 		return (sb);
2536 	}
2537 
2538 	for (c = 0; c < children; c++) {
2539 		sb = find_start_block(child[c]);
2540 		if (sb != MAXOFFSET_T) {
2541 			return (sb);
2542 		}
2543 	}
2544 	return (MAXOFFSET_T);
2545 }
2546 
2547 /*
2548  * Label an individual disk.  The name provided is the short name,
2549  * stripped of any leading /dev path.
2550  */
2551 int
2552 zpool_label_disk(libzfs_handle_t *hdl, zpool_handle_t *zhp, char *name)
2553 {
2554 	char path[MAXPATHLEN];
2555 	struct dk_gpt *vtoc;
2556 	int fd;
2557 	size_t resv = EFI_MIN_RESV_SIZE;
2558 	uint64_t slice_size;
2559 	diskaddr_t start_block;
2560 	char errbuf[1024];
2561 
2562 	/* prepare an error message just in case */
2563 	(void) snprintf(errbuf, sizeof (errbuf),
2564 	    dgettext(TEXT_DOMAIN, "cannot label '%s'"), name);
2565 
2566 	if (zhp) {
2567 		nvlist_t *nvroot;
2568 
2569 		verify(nvlist_lookup_nvlist(zhp->zpool_config,
2570 		    ZPOOL_CONFIG_VDEV_TREE, &nvroot) == 0);
2571 
2572 		if (zhp->zpool_start_block == 0)
2573 			start_block = find_start_block(nvroot);
2574 		else
2575 			start_block = zhp->zpool_start_block;
2576 		zhp->zpool_start_block = start_block;
2577 	} else {
2578 		/* new pool */
2579 		start_block = NEW_START_BLOCK;
2580 	}
2581 
2582 	(void) snprintf(path, sizeof (path), "%s/%s%s", RDISK_ROOT, name,
2583 	    BACKUP_SLICE);
2584 
2585 	if ((fd = open(path, O_RDWR | O_NDELAY)) < 0) {
2586 		/*
2587 		 * This shouldn't happen.  We've long since verified that this
2588 		 * is a valid device.
2589 		 */
2590 		zfs_error_aux(hdl,
2591 		    dgettext(TEXT_DOMAIN, "unable to open device"));
2592 		return (zfs_error(hdl, EZFS_OPENFAILED, errbuf));
2593 	}
2594 
2595 	if (efi_alloc_and_init(fd, EFI_NUMPAR, &vtoc) != 0) {
2596 		/*
2597 		 * The only way this can fail is if we run out of memory, or we
2598 		 * were unable to read the disk's capacity
2599 		 */
2600 		if (errno == ENOMEM)
2601 			(void) no_memory(hdl);
2602 
2603 		(void) close(fd);
2604 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2605 		    "unable to read disk capacity"), name);
2606 
2607 		return (zfs_error(hdl, EZFS_NOCAP, errbuf));
2608 	}
2609 
2610 	slice_size = vtoc->efi_last_u_lba + 1;
2611 	slice_size -= EFI_MIN_RESV_SIZE;
2612 	if (start_block == MAXOFFSET_T)
2613 		start_block = NEW_START_BLOCK;
2614 	slice_size -= start_block;
2615 
2616 	vtoc->efi_parts[0].p_start = start_block;
2617 	vtoc->efi_parts[0].p_size = slice_size;
2618 
2619 	/*
2620 	 * Why we use V_USR: V_BACKUP confuses users, and is considered
2621 	 * disposable by some EFI utilities (since EFI doesn't have a backup
2622 	 * slice).  V_UNASSIGNED is supposed to be used only for zero size
2623 	 * partitions, and efi_write() will fail if we use it.  V_ROOT, V_BOOT,
2624 	 * etc. were all pretty specific.  V_USR is as close to reality as we
2625 	 * can get, in the absence of V_OTHER.
2626 	 */
2627 	vtoc->efi_parts[0].p_tag = V_USR;
2628 	(void) strcpy(vtoc->efi_parts[0].p_name, "zfs");
2629 
2630 	vtoc->efi_parts[8].p_start = slice_size + start_block;
2631 	vtoc->efi_parts[8].p_size = resv;
2632 	vtoc->efi_parts[8].p_tag = V_RESERVED;
2633 
2634 	if (efi_write(fd, vtoc) != 0) {
2635 		/*
2636 		 * Some block drivers (like pcata) may not support EFI
2637 		 * GPT labels.  Print out a helpful error message dir-
2638 		 * ecting the user to manually label the disk and give
2639 		 * a specific slice.
2640 		 */
2641 		(void) close(fd);
2642 		efi_free(vtoc);
2643 
2644 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2645 		    "try using fdisk(1M) and then provide a specific slice"));
2646 		return (zfs_error(hdl, EZFS_LABELFAILED, errbuf));
2647 	}
2648 
2649 	(void) close(fd);
2650 	efi_free(vtoc);
2651 	return (0);
2652 }
2653 
2654 static boolean_t
2655 supported_dump_vdev_type(libzfs_handle_t *hdl, nvlist_t *config, char *errbuf)
2656 {
2657 	char *type;
2658 	nvlist_t **child;
2659 	uint_t children, c;
2660 
2661 	verify(nvlist_lookup_string(config, ZPOOL_CONFIG_TYPE, &type) == 0);
2662 	if (strcmp(type, VDEV_TYPE_RAIDZ) == 0 ||
2663 	    strcmp(type, VDEV_TYPE_FILE) == 0 ||
2664 	    strcmp(type, VDEV_TYPE_LOG) == 0 ||
2665 	    strcmp(type, VDEV_TYPE_MISSING) == 0) {
2666 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2667 		    "vdev type '%s' is not supported"), type);
2668 		(void) zfs_error(hdl, EZFS_VDEVNOTSUP, errbuf);
2669 		return (B_FALSE);
2670 	}
2671 	if (nvlist_lookup_nvlist_array(config, ZPOOL_CONFIG_CHILDREN,
2672 	    &child, &children) == 0) {
2673 		for (c = 0; c < children; c++) {
2674 			if (!supported_dump_vdev_type(hdl, child[c], errbuf))
2675 				return (B_FALSE);
2676 		}
2677 	}
2678 	return (B_TRUE);
2679 }
2680 
2681 /*
2682  * check if this zvol is allowable for use as a dump device; zero if
2683  * it is, > 0 if it isn't, < 0 if it isn't a zvol
2684  */
2685 int
2686 zvol_check_dump_config(char *arg)
2687 {
2688 	zpool_handle_t *zhp = NULL;
2689 	nvlist_t *config, *nvroot;
2690 	char *p, *volname;
2691 	nvlist_t **top;
2692 	uint_t toplevels;
2693 	libzfs_handle_t *hdl;
2694 	char errbuf[1024];
2695 	char poolname[ZPOOL_MAXNAMELEN];
2696 	int pathlen = strlen(ZVOL_FULL_DEV_DIR);
2697 	int ret = 1;
2698 
2699 	if (strncmp(arg, ZVOL_FULL_DEV_DIR, pathlen)) {
2700 		return (-1);
2701 	}
2702 
2703 	(void) snprintf(errbuf, sizeof (errbuf), dgettext(TEXT_DOMAIN,
2704 	    "dump is not supported on device '%s'"), arg);
2705 
2706 	if ((hdl = libzfs_init()) == NULL)
2707 		return (1);
2708 	libzfs_print_on_error(hdl, B_TRUE);
2709 
2710 	volname = arg + pathlen;
2711 
2712 	/* check the configuration of the pool */
2713 	if ((p = strchr(volname, '/')) == NULL) {
2714 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2715 		    "malformed dataset name"));
2716 		(void) zfs_error(hdl, EZFS_INVALIDNAME, errbuf);
2717 		return (1);
2718 	} else if (p - volname >= ZFS_MAXNAMELEN) {
2719 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2720 		    "dataset name is too long"));
2721 		(void) zfs_error(hdl, EZFS_NAMETOOLONG, errbuf);
2722 		return (1);
2723 	} else {
2724 		(void) strncpy(poolname, volname, p - volname);
2725 		poolname[p - volname] = '\0';
2726 	}
2727 
2728 	if ((zhp = zpool_open(hdl, poolname)) == NULL) {
2729 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2730 		    "could not open pool '%s'"), poolname);
2731 		(void) zfs_error(hdl, EZFS_OPENFAILED, errbuf);
2732 		goto out;
2733 	}
2734 	config = zpool_get_config(zhp, NULL);
2735 	if (nvlist_lookup_nvlist(config, ZPOOL_CONFIG_VDEV_TREE,
2736 	    &nvroot) != 0) {
2737 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2738 		    "could not obtain vdev configuration for  '%s'"), poolname);
2739 		(void) zfs_error(hdl, EZFS_INVALCONFIG, errbuf);
2740 		goto out;
2741 	}
2742 
2743 	verify(nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_CHILDREN,
2744 	    &top, &toplevels) == 0);
2745 	if (toplevels != 1) {
2746 		zfs_error_aux(hdl, dgettext(TEXT_DOMAIN,
2747 		    "'%s' has multiple top level vdevs"), poolname);
2748 		(void) zfs_error(hdl, EZFS_DEVOVERFLOW, errbuf);
2749 		goto out;
2750 	}
2751 
2752 	if (!supported_dump_vdev_type(hdl, top[0], errbuf)) {
2753 		goto out;
2754 	}
2755 	ret = 0;
2756 
2757 out:
2758 	if (zhp)
2759 		zpool_close(zhp);
2760 	libzfs_fini(hdl);
2761 	return (ret);
2762 }
2763