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 #include <alloca.h> 28 #include <assert.h> 29 #include <ctype.h> 30 #include <errno.h> 31 #include <devid.h> 32 #include <dirent.h> 33 #include <fcntl.h> 34 #include <libintl.h> 35 #include <stdio.h> 36 #include <stdlib.h> 37 #include <strings.h> 38 #include <unistd.h> 39 #include <zone.h> 40 #include <sys/efi_partition.h> 41 #include <sys/vtoc.h> 42 #include <sys/zfs_ioctl.h> 43 #include <sys/zio.h> 44 #include <strings.h> 45 46 #include "zfs_namecheck.h" 47 #include "zfs_prop.h" 48 #include "libzfs_impl.h" 49 50 static int read_efi_label(nvlist_t *config, diskaddr_t *sb); 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 /* 140 * zpool_get_all_props() has most likely failed because 141 * the pool is faulted, but if all we need is the top level 142 * vdev's guid then get it from the zhp config nvlist. 143 */ 144 if ((prop == ZPOOL_PROP_GUID) && 145 (nvlist_lookup_nvlist(zhp->zpool_config, 146 ZPOOL_CONFIG_VDEV_TREE, &nv) == 0) && 147 (nvlist_lookup_uint64(nv, ZPOOL_CONFIG_GUID, &value) 148 == 0)) { 149 return (value); 150 } 151 return (zpool_prop_default_numeric(prop)); 152 } 153 154 nvl = zhp->zpool_props; 155 if (nvlist_lookup_nvlist(nvl, zpool_prop_to_name(prop), &nv) == 0) { 156 verify(nvlist_lookup_uint64(nv, ZPROP_SOURCE, &value) == 0); 157 source = value; 158 verify(nvlist_lookup_uint64(nv, ZPROP_VALUE, &value) == 0); 159 } else { 160 source = ZPROP_SRC_DEFAULT; 161 value = zpool_prop_default_numeric(prop); 162 } 163 164 if (src) 165 *src = source; 166 167 return (value); 168 } 169 170 /* 171 * Map VDEV STATE to printed strings. 172 */ 173 char * 174 zpool_state_to_name(vdev_state_t state, vdev_aux_t aux) 175 { 176 switch (state) { 177 case VDEV_STATE_CLOSED: 178 case VDEV_STATE_OFFLINE: 179 return (gettext("OFFLINE")); 180 case VDEV_STATE_REMOVED: 181 return (gettext("REMOVED")); 182 case VDEV_STATE_CANT_OPEN: 183 if (aux == VDEV_AUX_CORRUPT_DATA || aux == VDEV_AUX_BAD_LOG) 184 return (gettext("FAULTED")); 185 else 186 return (gettext("UNAVAIL")); 187 case VDEV_STATE_FAULTED: 188 return (gettext("FAULTED")); 189 case VDEV_STATE_DEGRADED: 190 return (gettext("DEGRADED")); 191 case VDEV_STATE_HEALTHY: 192 return (gettext("ONLINE")); 193 } 194 195 return (gettext("UNKNOWN")); 196 } 197 198 /* 199 * Get a zpool property value for 'prop' and return the value in 200 * a pre-allocated buffer. 201 */ 202 int 203 zpool_get_prop(zpool_handle_t *zhp, zpool_prop_t prop, char *buf, size_t len, 204 zprop_source_t *srctype) 205 { 206 uint64_t intval; 207 const char *strval; 208 zprop_source_t src = ZPROP_SRC_NONE; 209 nvlist_t *nvroot; 210 vdev_stat_t *vs; 211 uint_t vsc; 212 213 if (zpool_get_state(zhp) == POOL_STATE_UNAVAIL) { 214 if (prop == ZPOOL_PROP_NAME) 215 (void) strlcpy(buf, zpool_get_name(zhp), len); 216 else if (prop == ZPOOL_PROP_HEALTH) 217 (void) strlcpy(buf, "FAULTED", len); 218 else 219 (void) strlcpy(buf, "-", len); 220 return (0); 221 } 222 223 if (zhp->zpool_props == NULL && zpool_get_all_props(zhp) && 224 prop != ZPOOL_PROP_NAME) 225 return (-1); 226 227 switch (zpool_prop_get_type(prop)) { 228 case PROP_TYPE_STRING: 229 (void) strlcpy(buf, zpool_get_prop_string(zhp, prop, &src), 230 len); 231 break; 232 233 case PROP_TYPE_NUMBER: 234 intval = zpool_get_prop_int(zhp, prop, &src); 235 236 switch (prop) { 237 case ZPOOL_PROP_SIZE: 238 case ZPOOL_PROP_USED: 239 case ZPOOL_PROP_AVAILABLE: 240 (void) zfs_nicenum(intval, buf, len); 241 break; 242 243 case ZPOOL_PROP_CAPACITY: 244 (void) snprintf(buf, len, "%llu%%", 245 (u_longlong_t)intval); 246 break; 247 248 case ZPOOL_PROP_HEALTH: 249 verify(nvlist_lookup_nvlist(zpool_get_config(zhp, NULL), 250 ZPOOL_CONFIG_VDEV_TREE, &nvroot) == 0); 251 verify(nvlist_lookup_uint64_array(nvroot, 252 ZPOOL_CONFIG_STATS, (uint64_t **)&vs, &vsc) == 0); 253 254 (void) strlcpy(buf, zpool_state_to_name(intval, 255 vs->vs_aux), len); 256 break; 257 default: 258 (void) snprintf(buf, len, "%llu", intval); 259 } 260 break; 261 262 case PROP_TYPE_INDEX: 263 intval = zpool_get_prop_int(zhp, prop, &src); 264 if (zpool_prop_index_to_string(prop, intval, &strval) 265 != 0) 266 return (-1); 267 (void) strlcpy(buf, strval, len); 268 break; 269 270 default: 271 abort(); 272 } 273 274 if (srctype) 275 *srctype = src; 276 277 return (0); 278 } 279 280 /* 281 * Check if the bootfs name has the same pool name as it is set to. 282 * Assuming bootfs is a valid dataset name. 283 */ 284 static boolean_t 285 bootfs_name_valid(const char *pool, char *bootfs) 286 { 287 int len = strlen(pool); 288 289 if (!zfs_name_valid(bootfs, ZFS_TYPE_FILESYSTEM|ZFS_TYPE_SNAPSHOT)) 290 return (B_FALSE); 291 292 if (strncmp(pool, bootfs, len) == 0 && 293 (bootfs[len] == '/' || bootfs[len] == '\0')) 294 return (B_TRUE); 295 296 return (B_FALSE); 297 } 298 299 /* 300 * Inspect the configuration to determine if any of the devices contain 301 * an EFI label. 302 */ 303 static boolean_t 304 pool_uses_efi(nvlist_t *config) 305 { 306 nvlist_t **child; 307 uint_t c, children; 308 309 if (nvlist_lookup_nvlist_array(config, ZPOOL_CONFIG_CHILDREN, 310 &child, &children) != 0) 311 return (read_efi_label(config, NULL) >= 0); 312 313 for (c = 0; c < children; c++) { 314 if (pool_uses_efi(child[c])) 315 return (B_TRUE); 316 } 317 return (B_FALSE); 318 } 319 320 /* 321 * Given an nvlist of zpool properties to be set, validate that they are 322 * correct, and parse any numeric properties (index, boolean, etc) if they are 323 * specified as strings. 324 */ 325 static nvlist_t * 326 zpool_valid_proplist(libzfs_handle_t *hdl, const char *poolname, 327 nvlist_t *props, uint64_t version, boolean_t create_or_import, char *errbuf) 328 { 329 nvpair_t *elem; 330 nvlist_t *retprops; 331 zpool_prop_t prop; 332 char *strval; 333 uint64_t intval; 334 char *slash; 335 struct stat64 statbuf; 336 zpool_handle_t *zhp; 337 nvlist_t *nvroot; 338 339 if (nvlist_alloc(&retprops, NV_UNIQUE_NAME, 0) != 0) { 340 (void) no_memory(hdl); 341 return (NULL); 342 } 343 344 elem = NULL; 345 while ((elem = nvlist_next_nvpair(props, elem)) != NULL) { 346 const char *propname = nvpair_name(elem); 347 348 /* 349 * Make sure this property is valid and applies to this type. 350 */ 351 if ((prop = zpool_name_to_prop(propname)) == ZPROP_INVAL) { 352 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 353 "invalid property '%s'"), propname); 354 (void) zfs_error(hdl, EZFS_BADPROP, errbuf); 355 goto error; 356 } 357 358 if (zpool_prop_readonly(prop)) { 359 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "'%s' " 360 "is readonly"), propname); 361 (void) zfs_error(hdl, EZFS_PROPREADONLY, errbuf); 362 goto error; 363 } 364 365 if (zprop_parse_value(hdl, elem, prop, ZFS_TYPE_POOL, retprops, 366 &strval, &intval, errbuf) != 0) 367 goto error; 368 369 /* 370 * Perform additional checking for specific properties. 371 */ 372 switch (prop) { 373 case ZPOOL_PROP_VERSION: 374 if (intval < version || intval > SPA_VERSION) { 375 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 376 "property '%s' number %d is invalid."), 377 propname, intval); 378 (void) zfs_error(hdl, EZFS_BADVERSION, errbuf); 379 goto error; 380 } 381 break; 382 383 case ZPOOL_PROP_BOOTFS: 384 if (create_or_import) { 385 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 386 "property '%s' cannot be set at creation " 387 "or import time"), propname); 388 (void) zfs_error(hdl, EZFS_BADPROP, errbuf); 389 goto error; 390 } 391 392 if (version < SPA_VERSION_BOOTFS) { 393 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 394 "pool must be upgraded to support " 395 "'%s' property"), propname); 396 (void) zfs_error(hdl, EZFS_BADVERSION, errbuf); 397 goto error; 398 } 399 400 /* 401 * bootfs property value has to be a dataset name and 402 * the dataset has to be in the same pool as it sets to. 403 */ 404 if (strval[0] != '\0' && !bootfs_name_valid(poolname, 405 strval)) { 406 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "'%s' " 407 "is an invalid name"), strval); 408 (void) zfs_error(hdl, EZFS_INVALIDNAME, errbuf); 409 goto error; 410 } 411 412 if ((zhp = zpool_open_canfail(hdl, poolname)) == NULL) { 413 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 414 "could not open pool '%s'"), poolname); 415 (void) zfs_error(hdl, EZFS_OPENFAILED, errbuf); 416 goto error; 417 } 418 verify(nvlist_lookup_nvlist(zpool_get_config(zhp, NULL), 419 ZPOOL_CONFIG_VDEV_TREE, &nvroot) == 0); 420 421 /* 422 * bootfs property cannot be set on a disk which has 423 * been EFI labeled. 424 */ 425 if (pool_uses_efi(nvroot)) { 426 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 427 "property '%s' not supported on " 428 "EFI labeled devices"), propname); 429 (void) zfs_error(hdl, EZFS_POOL_NOTSUP, errbuf); 430 zpool_close(zhp); 431 goto error; 432 } 433 zpool_close(zhp); 434 break; 435 436 case ZPOOL_PROP_ALTROOT: 437 if (!create_or_import) { 438 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 439 "property '%s' can only be set during pool " 440 "creation or import"), propname); 441 (void) zfs_error(hdl, EZFS_BADPROP, errbuf); 442 goto error; 443 } 444 445 if (strval[0] != '/') { 446 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 447 "bad alternate root '%s'"), strval); 448 (void) zfs_error(hdl, EZFS_BADPATH, errbuf); 449 goto error; 450 } 451 break; 452 453 case ZPOOL_PROP_CACHEFILE: 454 if (strval[0] == '\0') 455 break; 456 457 if (strcmp(strval, "none") == 0) 458 break; 459 460 if (strval[0] != '/') { 461 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 462 "property '%s' must be empty, an " 463 "absolute path, or 'none'"), propname); 464 (void) zfs_error(hdl, EZFS_BADPATH, errbuf); 465 goto error; 466 } 467 468 slash = strrchr(strval, '/'); 469 470 if (slash[1] == '\0' || strcmp(slash, "/.") == 0 || 471 strcmp(slash, "/..") == 0) { 472 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 473 "'%s' is not a valid file"), strval); 474 (void) zfs_error(hdl, EZFS_BADPATH, errbuf); 475 goto error; 476 } 477 478 *slash = '\0'; 479 480 if (strval[0] != '\0' && 481 (stat64(strval, &statbuf) != 0 || 482 !S_ISDIR(statbuf.st_mode))) { 483 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 484 "'%s' is not a valid directory"), 485 strval); 486 (void) zfs_error(hdl, EZFS_BADPATH, errbuf); 487 goto error; 488 } 489 490 *slash = '/'; 491 break; 492 } 493 } 494 495 return (retprops); 496 error: 497 nvlist_free(retprops); 498 return (NULL); 499 } 500 501 /* 502 * Set zpool property : propname=propval. 503 */ 504 int 505 zpool_set_prop(zpool_handle_t *zhp, const char *propname, const char *propval) 506 { 507 zfs_cmd_t zc = { 0 }; 508 int ret = -1; 509 char errbuf[1024]; 510 nvlist_t *nvl = NULL; 511 nvlist_t *realprops; 512 uint64_t version; 513 514 (void) snprintf(errbuf, sizeof (errbuf), 515 dgettext(TEXT_DOMAIN, "cannot set property for '%s'"), 516 zhp->zpool_name); 517 518 if (zhp->zpool_props == NULL && zpool_get_all_props(zhp)) 519 return (zfs_error(zhp->zpool_hdl, EZFS_POOLPROPS, errbuf)); 520 521 if (nvlist_alloc(&nvl, NV_UNIQUE_NAME, 0) != 0) 522 return (no_memory(zhp->zpool_hdl)); 523 524 if (nvlist_add_string(nvl, propname, propval) != 0) { 525 nvlist_free(nvl); 526 return (no_memory(zhp->zpool_hdl)); 527 } 528 529 version = zpool_get_prop_int(zhp, ZPOOL_PROP_VERSION, NULL); 530 if ((realprops = zpool_valid_proplist(zhp->zpool_hdl, 531 zhp->zpool_name, nvl, version, B_FALSE, errbuf)) == NULL) { 532 nvlist_free(nvl); 533 return (-1); 534 } 535 536 nvlist_free(nvl); 537 nvl = realprops; 538 539 /* 540 * Execute the corresponding ioctl() to set this property. 541 */ 542 (void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name)); 543 544 if (zcmd_write_src_nvlist(zhp->zpool_hdl, &zc, nvl) != 0) { 545 nvlist_free(nvl); 546 return (-1); 547 } 548 549 ret = zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_POOL_SET_PROPS, &zc); 550 551 zcmd_free_nvlists(&zc); 552 nvlist_free(nvl); 553 554 if (ret) 555 (void) zpool_standard_error(zhp->zpool_hdl, errno, errbuf); 556 else 557 (void) zpool_props_refresh(zhp); 558 559 return (ret); 560 } 561 562 int 563 zpool_expand_proplist(zpool_handle_t *zhp, zprop_list_t **plp) 564 { 565 libzfs_handle_t *hdl = zhp->zpool_hdl; 566 zprop_list_t *entry; 567 char buf[ZFS_MAXPROPLEN]; 568 569 if (zprop_expand_list(hdl, plp, ZFS_TYPE_POOL) != 0) 570 return (-1); 571 572 for (entry = *plp; entry != NULL; entry = entry->pl_next) { 573 574 if (entry->pl_fixed) 575 continue; 576 577 if (entry->pl_prop != ZPROP_INVAL && 578 zpool_get_prop(zhp, entry->pl_prop, buf, sizeof (buf), 579 NULL) == 0) { 580 if (strlen(buf) > entry->pl_width) 581 entry->pl_width = strlen(buf); 582 } 583 } 584 585 return (0); 586 } 587 588 589 /* 590 * Validate the given pool name, optionally putting an extended error message in 591 * 'buf'. 592 */ 593 boolean_t 594 zpool_name_valid(libzfs_handle_t *hdl, boolean_t isopen, const char *pool) 595 { 596 namecheck_err_t why; 597 char what; 598 int ret; 599 600 ret = pool_namecheck(pool, &why, &what); 601 602 /* 603 * The rules for reserved pool names were extended at a later point. 604 * But we need to support users with existing pools that may now be 605 * invalid. So we only check for this expanded set of names during a 606 * create (or import), and only in userland. 607 */ 608 if (ret == 0 && !isopen && 609 (strncmp(pool, "mirror", 6) == 0 || 610 strncmp(pool, "raidz", 5) == 0 || 611 strncmp(pool, "spare", 5) == 0 || 612 strcmp(pool, "log") == 0)) { 613 if (hdl != NULL) 614 zfs_error_aux(hdl, 615 dgettext(TEXT_DOMAIN, "name is reserved")); 616 return (B_FALSE); 617 } 618 619 620 if (ret != 0) { 621 if (hdl != NULL) { 622 switch (why) { 623 case NAME_ERR_TOOLONG: 624 zfs_error_aux(hdl, 625 dgettext(TEXT_DOMAIN, "name is too long")); 626 break; 627 628 case NAME_ERR_INVALCHAR: 629 zfs_error_aux(hdl, 630 dgettext(TEXT_DOMAIN, "invalid character " 631 "'%c' in pool name"), what); 632 break; 633 634 case NAME_ERR_NOLETTER: 635 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 636 "name must begin with a letter")); 637 break; 638 639 case NAME_ERR_RESERVED: 640 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 641 "name is reserved")); 642 break; 643 644 case NAME_ERR_DISKLIKE: 645 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 646 "pool name is reserved")); 647 break; 648 649 case NAME_ERR_LEADING_SLASH: 650 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 651 "leading slash in name")); 652 break; 653 654 case NAME_ERR_EMPTY_COMPONENT: 655 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 656 "empty component in name")); 657 break; 658 659 case NAME_ERR_TRAILING_SLASH: 660 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 661 "trailing slash in name")); 662 break; 663 664 case NAME_ERR_MULTIPLE_AT: 665 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 666 "multiple '@' delimiters in name")); 667 break; 668 669 } 670 } 671 return (B_FALSE); 672 } 673 674 return (B_TRUE); 675 } 676 677 /* 678 * Open a handle to the given pool, even if the pool is currently in the FAULTED 679 * state. 680 */ 681 zpool_handle_t * 682 zpool_open_canfail(libzfs_handle_t *hdl, const char *pool) 683 { 684 zpool_handle_t *zhp; 685 boolean_t missing; 686 687 /* 688 * Make sure the pool name is valid. 689 */ 690 if (!zpool_name_valid(hdl, B_TRUE, pool)) { 691 (void) zfs_error_fmt(hdl, EZFS_INVALIDNAME, 692 dgettext(TEXT_DOMAIN, "cannot open '%s'"), 693 pool); 694 return (NULL); 695 } 696 697 if ((zhp = zfs_alloc(hdl, sizeof (zpool_handle_t))) == NULL) 698 return (NULL); 699 700 zhp->zpool_hdl = hdl; 701 (void) strlcpy(zhp->zpool_name, pool, sizeof (zhp->zpool_name)); 702 703 if (zpool_refresh_stats(zhp, &missing) != 0) { 704 zpool_close(zhp); 705 return (NULL); 706 } 707 708 if (missing) { 709 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "no such pool")); 710 (void) zfs_error_fmt(hdl, EZFS_NOENT, 711 dgettext(TEXT_DOMAIN, "cannot open '%s'"), pool); 712 zpool_close(zhp); 713 return (NULL); 714 } 715 716 return (zhp); 717 } 718 719 /* 720 * Like the above, but silent on error. Used when iterating over pools (because 721 * the configuration cache may be out of date). 722 */ 723 int 724 zpool_open_silent(libzfs_handle_t *hdl, const char *pool, zpool_handle_t **ret) 725 { 726 zpool_handle_t *zhp; 727 boolean_t missing; 728 729 if ((zhp = zfs_alloc(hdl, sizeof (zpool_handle_t))) == NULL) 730 return (-1); 731 732 zhp->zpool_hdl = hdl; 733 (void) strlcpy(zhp->zpool_name, pool, sizeof (zhp->zpool_name)); 734 735 if (zpool_refresh_stats(zhp, &missing) != 0) { 736 zpool_close(zhp); 737 return (-1); 738 } 739 740 if (missing) { 741 zpool_close(zhp); 742 *ret = NULL; 743 return (0); 744 } 745 746 *ret = zhp; 747 return (0); 748 } 749 750 /* 751 * Similar to zpool_open_canfail(), but refuses to open pools in the faulted 752 * state. 753 */ 754 zpool_handle_t * 755 zpool_open(libzfs_handle_t *hdl, const char *pool) 756 { 757 zpool_handle_t *zhp; 758 759 if ((zhp = zpool_open_canfail(hdl, pool)) == NULL) 760 return (NULL); 761 762 if (zhp->zpool_state == POOL_STATE_UNAVAIL) { 763 (void) zfs_error_fmt(hdl, EZFS_POOLUNAVAIL, 764 dgettext(TEXT_DOMAIN, "cannot open '%s'"), zhp->zpool_name); 765 zpool_close(zhp); 766 return (NULL); 767 } 768 769 return (zhp); 770 } 771 772 /* 773 * Close the handle. Simply frees the memory associated with the handle. 774 */ 775 void 776 zpool_close(zpool_handle_t *zhp) 777 { 778 if (zhp->zpool_config) 779 nvlist_free(zhp->zpool_config); 780 if (zhp->zpool_old_config) 781 nvlist_free(zhp->zpool_old_config); 782 if (zhp->zpool_props) 783 nvlist_free(zhp->zpool_props); 784 free(zhp); 785 } 786 787 /* 788 * Return the name of the pool. 789 */ 790 const char * 791 zpool_get_name(zpool_handle_t *zhp) 792 { 793 return (zhp->zpool_name); 794 } 795 796 797 /* 798 * Return the state of the pool (ACTIVE or UNAVAILABLE) 799 */ 800 int 801 zpool_get_state(zpool_handle_t *zhp) 802 { 803 return (zhp->zpool_state); 804 } 805 806 /* 807 * Create the named pool, using the provided vdev list. It is assumed 808 * that the consumer has already validated the contents of the nvlist, so we 809 * don't have to worry about error semantics. 810 */ 811 int 812 zpool_create(libzfs_handle_t *hdl, const char *pool, nvlist_t *nvroot, 813 nvlist_t *props, nvlist_t *fsprops) 814 { 815 zfs_cmd_t zc = { 0 }; 816 nvlist_t *zc_fsprops = NULL; 817 nvlist_t *zc_props = NULL; 818 char msg[1024]; 819 char *altroot; 820 int ret = -1; 821 822 (void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN, 823 "cannot create '%s'"), pool); 824 825 if (!zpool_name_valid(hdl, B_FALSE, pool)) 826 return (zfs_error(hdl, EZFS_INVALIDNAME, msg)); 827 828 if (zcmd_write_conf_nvlist(hdl, &zc, nvroot) != 0) 829 return (-1); 830 831 if (props) { 832 if ((zc_props = zpool_valid_proplist(hdl, pool, props, 833 SPA_VERSION_1, B_TRUE, msg)) == NULL) { 834 goto create_failed; 835 } 836 } 837 838 if (fsprops) { 839 uint64_t zoned; 840 char *zonestr; 841 842 zoned = ((nvlist_lookup_string(fsprops, 843 zfs_prop_to_name(ZFS_PROP_ZONED), &zonestr) == 0) && 844 strcmp(zonestr, "on") == 0); 845 846 if ((zc_fsprops = zfs_valid_proplist(hdl, 847 ZFS_TYPE_FILESYSTEM, fsprops, zoned, NULL, msg)) == NULL) { 848 goto create_failed; 849 } 850 if (!zc_props && 851 (nvlist_alloc(&zc_props, NV_UNIQUE_NAME, 0) != 0)) { 852 goto create_failed; 853 } 854 if (nvlist_add_nvlist(zc_props, 855 ZPOOL_ROOTFS_PROPS, zc_fsprops) != 0) { 856 goto create_failed; 857 } 858 } 859 860 if (zc_props && zcmd_write_src_nvlist(hdl, &zc, zc_props) != 0) 861 goto create_failed; 862 863 (void) strlcpy(zc.zc_name, pool, sizeof (zc.zc_name)); 864 865 if ((ret = zfs_ioctl(hdl, ZFS_IOC_POOL_CREATE, &zc)) != 0) { 866 867 zcmd_free_nvlists(&zc); 868 nvlist_free(zc_props); 869 nvlist_free(zc_fsprops); 870 871 switch (errno) { 872 case EBUSY: 873 /* 874 * This can happen if the user has specified the same 875 * device multiple times. We can't reliably detect this 876 * until we try to add it and see we already have a 877 * label. 878 */ 879 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 880 "one or more vdevs refer to the same device")); 881 return (zfs_error(hdl, EZFS_BADDEV, msg)); 882 883 case EOVERFLOW: 884 /* 885 * This occurs when one of the devices is below 886 * SPA_MINDEVSIZE. Unfortunately, we can't detect which 887 * device was the problem device since there's no 888 * reliable way to determine device size from userland. 889 */ 890 { 891 char buf[64]; 892 893 zfs_nicenum(SPA_MINDEVSIZE, buf, sizeof (buf)); 894 895 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 896 "one or more devices is less than the " 897 "minimum size (%s)"), buf); 898 } 899 return (zfs_error(hdl, EZFS_BADDEV, msg)); 900 901 case ENOSPC: 902 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 903 "one or more devices is out of space")); 904 return (zfs_error(hdl, EZFS_BADDEV, msg)); 905 906 case ENOTBLK: 907 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 908 "cache device must be a disk or disk slice")); 909 return (zfs_error(hdl, EZFS_BADDEV, msg)); 910 911 default: 912 return (zpool_standard_error(hdl, errno, msg)); 913 } 914 } 915 916 /* 917 * If this is an alternate root pool, then we automatically set the 918 * mountpoint of the root dataset to be '/'. 919 */ 920 if (nvlist_lookup_string(props, zpool_prop_to_name(ZPOOL_PROP_ALTROOT), 921 &altroot) == 0) { 922 zfs_handle_t *zhp; 923 924 verify((zhp = zfs_open(hdl, pool, ZFS_TYPE_DATASET)) != NULL); 925 verify(zfs_prop_set(zhp, zfs_prop_to_name(ZFS_PROP_MOUNTPOINT), 926 "/") == 0); 927 928 zfs_close(zhp); 929 } 930 931 create_failed: 932 zcmd_free_nvlists(&zc); 933 nvlist_free(zc_props); 934 nvlist_free(zc_fsprops); 935 return (ret); 936 } 937 938 /* 939 * Destroy the given pool. It is up to the caller to ensure that there are no 940 * datasets left in the pool. 941 */ 942 int 943 zpool_destroy(zpool_handle_t *zhp) 944 { 945 zfs_cmd_t zc = { 0 }; 946 zfs_handle_t *zfp = NULL; 947 libzfs_handle_t *hdl = zhp->zpool_hdl; 948 char msg[1024]; 949 950 if (zhp->zpool_state == POOL_STATE_ACTIVE && 951 (zfp = zfs_open(zhp->zpool_hdl, zhp->zpool_name, 952 ZFS_TYPE_FILESYSTEM)) == NULL) 953 return (-1); 954 955 if (zpool_remove_zvol_links(zhp) != 0) 956 return (-1); 957 958 (void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name)); 959 960 if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_POOL_DESTROY, &zc) != 0) { 961 (void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN, 962 "cannot destroy '%s'"), zhp->zpool_name); 963 964 if (errno == EROFS) { 965 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 966 "one or more devices is read only")); 967 (void) zfs_error(hdl, EZFS_BADDEV, msg); 968 } else { 969 (void) zpool_standard_error(hdl, errno, msg); 970 } 971 972 if (zfp) 973 zfs_close(zfp); 974 return (-1); 975 } 976 977 if (zfp) { 978 remove_mountpoint(zfp); 979 zfs_close(zfp); 980 } 981 982 return (0); 983 } 984 985 /* 986 * Add the given vdevs to the pool. The caller must have already performed the 987 * necessary verification to ensure that the vdev specification is well-formed. 988 */ 989 int 990 zpool_add(zpool_handle_t *zhp, nvlist_t *nvroot) 991 { 992 zfs_cmd_t zc = { 0 }; 993 int ret; 994 libzfs_handle_t *hdl = zhp->zpool_hdl; 995 char msg[1024]; 996 nvlist_t **spares, **l2cache; 997 uint_t nspares, nl2cache; 998 999 (void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN, 1000 "cannot add to '%s'"), zhp->zpool_name); 1001 1002 if (zpool_get_prop_int(zhp, ZPOOL_PROP_VERSION, NULL) < 1003 SPA_VERSION_SPARES && 1004 nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_SPARES, 1005 &spares, &nspares) == 0) { 1006 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "pool must be " 1007 "upgraded to add hot spares")); 1008 return (zfs_error(hdl, EZFS_BADVERSION, msg)); 1009 } 1010 1011 if (zpool_get_prop_int(zhp, ZPOOL_PROP_VERSION, NULL) < 1012 SPA_VERSION_L2CACHE && 1013 nvlist_lookup_nvlist_array(nvroot, ZPOOL_CONFIG_L2CACHE, 1014 &l2cache, &nl2cache) == 0) { 1015 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "pool must be " 1016 "upgraded to add cache devices")); 1017 return (zfs_error(hdl, EZFS_BADVERSION, msg)); 1018 } 1019 1020 if (zcmd_write_conf_nvlist(hdl, &zc, nvroot) != 0) 1021 return (-1); 1022 (void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name)); 1023 1024 if (zfs_ioctl(zhp->zpool_hdl, ZFS_IOC_VDEV_ADD, &zc) != 0) { 1025 switch (errno) { 1026 case EBUSY: 1027 /* 1028 * This can happen if the user has specified the same 1029 * device multiple times. We can't reliably detect this 1030 * until we try to add it and see we already have a 1031 * label. 1032 */ 1033 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 1034 "one or more vdevs refer to the same device")); 1035 (void) zfs_error(hdl, EZFS_BADDEV, msg); 1036 break; 1037 1038 case EOVERFLOW: 1039 /* 1040 * This occurrs when one of the devices is below 1041 * SPA_MINDEVSIZE. Unfortunately, we can't detect which 1042 * device was the problem device since there's no 1043 * reliable way to determine device size from userland. 1044 */ 1045 { 1046 char buf[64]; 1047 1048 zfs_nicenum(SPA_MINDEVSIZE, buf, sizeof (buf)); 1049 1050 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 1051 "device is less than the minimum " 1052 "size (%s)"), buf); 1053 } 1054 (void) zfs_error(hdl, EZFS_BADDEV, msg); 1055 break; 1056 1057 case ENOTSUP: 1058 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 1059 "pool must be upgraded to add these vdevs")); 1060 (void) zfs_error(hdl, EZFS_BADVERSION, msg); 1061 break; 1062 1063 case EDOM: 1064 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 1065 "root pool can not have multiple vdevs" 1066 " or separate logs")); 1067 (void) zfs_error(hdl, EZFS_POOL_NOTSUP, msg); 1068 break; 1069 1070 case ENOTBLK: 1071 zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, 1072 "cache device must be a disk or disk slice")); 1073 (void) zfs_error(hdl, EZFS_BADDEV, msg); 1074 break; 1075 1076 default: 1077 (void) zpool_standard_error(hdl, errno, msg); 1078 } 1079 1080 ret = -1; 1081 } else { 1082 ret = 0; 1083 } 1084 1085 zcmd_free_nvlists(&zc); 1086 1087 return (ret); 1088 } 1089 1090 /*