Print this page
1693 persistent 'comment' field for a zpool


 188 
 189                 cap = (size == 0) ? 0 : (alloc * 100 / size);
 190                 spa_prop_add_list(*nvp, ZPOOL_PROP_CAPACITY, NULL, cap, src);
 191 
 192                 spa_prop_add_list(*nvp, ZPOOL_PROP_DEDUPRATIO, NULL,
 193                     ddt_get_pool_dedup_ratio(spa), src);
 194 
 195                 spa_prop_add_list(*nvp, ZPOOL_PROP_HEALTH, NULL,
 196                     spa->spa_root_vdev->vdev_state, src);
 197 
 198                 version = spa_version(spa);
 199                 if (version == zpool_prop_default_numeric(ZPOOL_PROP_VERSION))
 200                         src = ZPROP_SRC_DEFAULT;
 201                 else
 202                         src = ZPROP_SRC_LOCAL;
 203                 spa_prop_add_list(*nvp, ZPOOL_PROP_VERSION, NULL, version, src);
 204         }
 205 
 206         spa_prop_add_list(*nvp, ZPOOL_PROP_GUID, NULL, spa_guid(spa), src);
 207 





 208         if (spa->spa_root != NULL)
 209                 spa_prop_add_list(*nvp, ZPOOL_PROP_ALTROOT, spa->spa_root,
 210                     0, ZPROP_SRC_LOCAL);
 211 
 212         if ((dp = list_head(&spa->spa_config_list)) != NULL) {
 213                 if (dp->scd_path == NULL) {
 214                         spa_prop_add_list(*nvp, ZPOOL_PROP_CACHEFILE,
 215                             "none", 0, ZPROP_SRC_LOCAL);
 216                 } else if (strcmp(dp->scd_path, spa_config_path) != 0) {
 217                         spa_prop_add_list(*nvp, ZPOOL_PROP_CACHEFILE,
 218                             dp->scd_path, 0, ZPROP_SRC_LOCAL);
 219                 }
 220         }
 221 }
 222 
 223 /*
 224  * Get zpool property values.
 225  */
 226 int
 227 spa_prop_get(spa_t *spa, nvlist_t **nvp)


 327         return (0);
 328 }
 329 
 330 /*
 331  * Validate the given pool properties nvlist and modify the list
 332  * for the property values to be set.
 333  */
 334 static int
 335 spa_prop_validate(spa_t *spa, nvlist_t *props)
 336 {
 337         nvpair_t *elem;
 338         int error = 0, reset_bootfs = 0;
 339         uint64_t objnum;
 340 
 341         elem = NULL;
 342         while ((elem = nvlist_next_nvpair(props, elem)) != NULL) {
 343                 zpool_prop_t prop;
 344                 char *propname, *strval;
 345                 uint64_t intval;
 346                 objset_t *os;
 347                 char *slash;
 348 
 349                 propname = nvpair_name(elem);
 350 
 351                 if ((prop = zpool_name_to_prop(propname)) == ZPROP_INVAL)
 352                         return (EINVAL);
 353 
 354                 switch (prop) {
 355                 case ZPOOL_PROP_VERSION:
 356                         error = nvpair_value_uint64(elem, &intval);
 357                         if (!error &&
 358                             (intval < spa_version(spa) || intval > SPA_VERSION))
 359                                 error = EINVAL;
 360                         break;
 361 
 362                 case ZPOOL_PROP_DELEGATION:
 363                 case ZPOOL_PROP_AUTOREPLACE:
 364                 case ZPOOL_PROP_LISTSNAPS:
 365                 case ZPOOL_PROP_AUTOEXPAND:
 366                         error = nvpair_value_uint64(elem, &intval);
 367                         if (!error && intval > 1)


 447 
 448                         if (strval[0] == '\0')
 449                                 break;
 450 
 451                         if (strcmp(strval, "none") == 0)
 452                                 break;
 453 
 454                         if (strval[0] != '/') {
 455                                 error = EINVAL;
 456                                 break;
 457                         }
 458 
 459                         slash = strrchr(strval, '/');
 460                         ASSERT(slash != NULL);
 461 
 462                         if (slash[1] == '\0' || strcmp(slash, "/.") == 0 ||
 463                             strcmp(slash, "/..") == 0)
 464                                 error = EINVAL;
 465                         break;
 466 




















 467                 case ZPOOL_PROP_DEDUPDITTO:
 468                         if (spa_version(spa) < SPA_VERSION_DEDUP)
 469                                 error = ENOTSUP;
 470                         else
 471                                 error = nvpair_value_uint64(elem, &intval);
 472                         if (error == 0 &&
 473                             intval != 0 && intval < ZIO_DEDUPDITTO_MIN)
 474                                 error = EINVAL;
 475                         break;
 476                 }
 477 
 478                 if (error)
 479                         break;
 480         }
 481 
 482         if (!error && reset_bootfs) {
 483                 error = nvlist_remove(props,
 484                     zpool_prop_to_name(ZPOOL_PROP_BOOTFS), DATA_TYPE_STRING);
 485 
 486                 if (!error) {


1025                 nvlist_free(spa->spa_spares.sav_config);
1026                 spa->spa_spares.sav_config = NULL;
1027         }
1028         spa->spa_spares.sav_count = 0;
1029 
1030         for (i = 0; i < spa->spa_l2cache.sav_count; i++)
1031                 vdev_free(spa->spa_l2cache.sav_vdevs[i]);
1032         if (spa->spa_l2cache.sav_vdevs) {
1033                 kmem_free(spa->spa_l2cache.sav_vdevs,
1034                     spa->spa_l2cache.sav_count * sizeof (void *));
1035                 spa->spa_l2cache.sav_vdevs = NULL;
1036         }
1037         if (spa->spa_l2cache.sav_config) {
1038                 nvlist_free(spa->spa_l2cache.sav_config);
1039                 spa->spa_l2cache.sav_config = NULL;
1040         }
1041         spa->spa_l2cache.sav_count = 0;
1042 
1043         spa->spa_async_suspended = 0;
1044 





1045         spa_config_exit(spa, SCL_ALL, FTAG);
1046 }
1047 
1048 /*
1049  * Load (or re-load) the current list of vdevs describing the active spares for
1050  * this pool.  When this is called, we have some form of basic information in
1051  * 'spa_spares.sav_config'.  We parse this into vdevs, try to open them, and
1052  * then re-generate a more complete list including status information.
1053  */
1054 static void
1055 spa_load_spares(spa_t *spa)
1056 {
1057         nvlist_t **spares;
1058         uint_t nspares;
1059         int i;
1060         vdev_t *vd, *tvd;
1061 
1062         ASSERT(spa_config_held(spa, SCL_ALL, RW_WRITER) == SCL_ALL);
1063 
1064         /*


1740          * If every disk has been moved to the new pool, or if we never
1741          * even attempted to look at them, then we split them off for
1742          * good.
1743          */
1744         if (!attempt_reopen || gcount == extracted) {
1745                 for (i = 0; i < gcount; i++)
1746                         if (vd[i] != NULL)
1747                                 vdev_split(vd[i]);
1748                 vdev_reopen(spa->spa_root_vdev);
1749         }
1750 
1751         kmem_free(vd, gcount * sizeof (vdev_t *));
1752 }
1753 
1754 static int
1755 spa_load(spa_t *spa, spa_load_state_t state, spa_import_type_t type,
1756     boolean_t mosconfig)
1757 {
1758         nvlist_t *config = spa->spa_config;
1759         char *ereport = FM_EREPORT_ZFS_POOL;

1760         int error;
1761         uint64_t pool_guid;
1762         nvlist_t *nvl;
1763 
1764         if (nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_GUID, &pool_guid))
1765                 return (EINVAL);
1766 




1767         /*
1768          * Versioning wasn't explicitly added to the label until later, so if
1769          * it's not present treat it as the initial version.
1770          */
1771         if (nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
1772             &spa->spa_ubsync.ub_version) != 0)
1773                 spa->spa_ubsync.ub_version = SPA_VERSION_INITIAL;
1774 
1775         (void) nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_TXG,
1776             &spa->spa_config_txg);
1777 
1778         if ((state == SPA_LOAD_IMPORT || state == SPA_LOAD_TRYIMPORT) &&
1779             spa_guid_exists(pool_guid, 0)) {
1780                 error = EEXIST;
1781         } else {
1782                 spa->spa_config_guid = pool_guid;
1783 
1784                 if (nvlist_lookup_nvlist(config, ZPOOL_CONFIG_SPLIT,
1785                     &nvl) == 0) {
1786                         VERIFY(nvlist_dup(nvl, &spa->spa_config_splitting,


5354                                 spa->spa_uberblock.ub_version = intval;
5355                                 vdev_config_dirty(spa->spa_root_vdev);
5356                         }
5357                         break;
5358 
5359                 case ZPOOL_PROP_ALTROOT:
5360                         /*
5361                          * 'altroot' is a non-persistent property. It should
5362                          * have been set temporarily at creation or import time.
5363                          */
5364                         ASSERT(spa->spa_root != NULL);
5365                         break;
5366 
5367                 case ZPOOL_PROP_READONLY:
5368                 case ZPOOL_PROP_CACHEFILE:
5369                         /*
5370                          * 'readonly' and 'cachefile' are also non-persisitent
5371                          * properties.
5372                          */
5373                         break;














5374                 default:
5375                         /*
5376                          * Set pool property values in the poolprops mos object.
5377                          */
5378                         if (spa->spa_pool_props_object == 0) {
5379                                 VERIFY((spa->spa_pool_props_object =
5380                                     zap_create(mos, DMU_OT_POOL_PROPS,
5381                                     DMU_OT_NONE, 0, tx)) > 0);
5382 
5383                                 VERIFY(zap_update(mos,
5384                                     DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_PROPS,
5385                                     8, 1, &spa->spa_pool_props_object, tx)
5386                                     == 0);
5387                         }
5388 
5389                         /* normalize the property name */
5390                         propname = zpool_prop_to_name(prop);
5391                         proptype = zpool_prop_get_type(prop);
5392 
5393                         if (nvpair_type(elem) == DATA_TYPE_STRING) {




 188 
 189                 cap = (size == 0) ? 0 : (alloc * 100 / size);
 190                 spa_prop_add_list(*nvp, ZPOOL_PROP_CAPACITY, NULL, cap, src);
 191 
 192                 spa_prop_add_list(*nvp, ZPOOL_PROP_DEDUPRATIO, NULL,
 193                     ddt_get_pool_dedup_ratio(spa), src);
 194 
 195                 spa_prop_add_list(*nvp, ZPOOL_PROP_HEALTH, NULL,
 196                     spa->spa_root_vdev->vdev_state, src);
 197 
 198                 version = spa_version(spa);
 199                 if (version == zpool_prop_default_numeric(ZPOOL_PROP_VERSION))
 200                         src = ZPROP_SRC_DEFAULT;
 201                 else
 202                         src = ZPROP_SRC_LOCAL;
 203                 spa_prop_add_list(*nvp, ZPOOL_PROP_VERSION, NULL, version, src);
 204         }
 205 
 206         spa_prop_add_list(*nvp, ZPOOL_PROP_GUID, NULL, spa_guid(spa), src);
 207 
 208         if (spa->spa_comment != NULL) {
 209                 spa_prop_add_list(*nvp, ZPOOL_PROP_COMMENT, spa->spa_comment,
 210                     0, ZPROP_SRC_LOCAL);
 211         }
 212 
 213         if (spa->spa_root != NULL)
 214                 spa_prop_add_list(*nvp, ZPOOL_PROP_ALTROOT, spa->spa_root,
 215                     0, ZPROP_SRC_LOCAL);
 216 
 217         if ((dp = list_head(&spa->spa_config_list)) != NULL) {
 218                 if (dp->scd_path == NULL) {
 219                         spa_prop_add_list(*nvp, ZPOOL_PROP_CACHEFILE,
 220                             "none", 0, ZPROP_SRC_LOCAL);
 221                 } else if (strcmp(dp->scd_path, spa_config_path) != 0) {
 222                         spa_prop_add_list(*nvp, ZPOOL_PROP_CACHEFILE,
 223                             dp->scd_path, 0, ZPROP_SRC_LOCAL);
 224                 }
 225         }
 226 }
 227 
 228 /*
 229  * Get zpool property values.
 230  */
 231 int
 232 spa_prop_get(spa_t *spa, nvlist_t **nvp)


 332         return (0);
 333 }
 334 
 335 /*
 336  * Validate the given pool properties nvlist and modify the list
 337  * for the property values to be set.
 338  */
 339 static int
 340 spa_prop_validate(spa_t *spa, nvlist_t *props)
 341 {
 342         nvpair_t *elem;
 343         int error = 0, reset_bootfs = 0;
 344         uint64_t objnum;
 345 
 346         elem = NULL;
 347         while ((elem = nvlist_next_nvpair(props, elem)) != NULL) {
 348                 zpool_prop_t prop;
 349                 char *propname, *strval;
 350                 uint64_t intval;
 351                 objset_t *os;
 352                 char *slash, *check;
 353 
 354                 propname = nvpair_name(elem);
 355 
 356                 if ((prop = zpool_name_to_prop(propname)) == ZPROP_INVAL)
 357                         return (EINVAL);
 358 
 359                 switch (prop) {
 360                 case ZPOOL_PROP_VERSION:
 361                         error = nvpair_value_uint64(elem, &intval);
 362                         if (!error &&
 363                             (intval < spa_version(spa) || intval > SPA_VERSION))
 364                                 error = EINVAL;
 365                         break;
 366 
 367                 case ZPOOL_PROP_DELEGATION:
 368                 case ZPOOL_PROP_AUTOREPLACE:
 369                 case ZPOOL_PROP_LISTSNAPS:
 370                 case ZPOOL_PROP_AUTOEXPAND:
 371                         error = nvpair_value_uint64(elem, &intval);
 372                         if (!error && intval > 1)


 452 
 453                         if (strval[0] == '\0')
 454                                 break;
 455 
 456                         if (strcmp(strval, "none") == 0)
 457                                 break;
 458 
 459                         if (strval[0] != '/') {
 460                                 error = EINVAL;
 461                                 break;
 462                         }
 463 
 464                         slash = strrchr(strval, '/');
 465                         ASSERT(slash != NULL);
 466 
 467                         if (slash[1] == '\0' || strcmp(slash, "/.") == 0 ||
 468                             strcmp(slash, "/..") == 0)
 469                                 error = EINVAL;
 470                         break;
 471 
 472                 case ZPOOL_PROP_COMMENT:
 473                         if ((error = nvpair_value_string(elem, &strval)) != 0)
 474                                 break;
 475                         for (check = strval; *check != '\0'; check++) {
 476                                 /*
 477                                  * The kernel doesn't have an easy isprint()
 478                                  * check.  For this kernel check, we merely
 479                                  * check ASCII apart from DEL.  Fix this if
 480                                  * there is an easy-to-use kernel isprint().
 481                                  */
 482                                 if (*check >= 0x7f) {
 483                                         error = EINVAL;
 484                                         break;
 485                                 }
 486                                 check++;
 487                         }
 488                         if (strlen(strval) > ZPROP_MAX_COMMENT)
 489                                 error = E2BIG;
 490                         break;
 491 
 492                 case ZPOOL_PROP_DEDUPDITTO:
 493                         if (spa_version(spa) < SPA_VERSION_DEDUP)
 494                                 error = ENOTSUP;
 495                         else
 496                                 error = nvpair_value_uint64(elem, &intval);
 497                         if (error == 0 &&
 498                             intval != 0 && intval < ZIO_DEDUPDITTO_MIN)
 499                                 error = EINVAL;
 500                         break;
 501                 }
 502 
 503                 if (error)
 504                         break;
 505         }
 506 
 507         if (!error && reset_bootfs) {
 508                 error = nvlist_remove(props,
 509                     zpool_prop_to_name(ZPOOL_PROP_BOOTFS), DATA_TYPE_STRING);
 510 
 511                 if (!error) {


1050                 nvlist_free(spa->spa_spares.sav_config);
1051                 spa->spa_spares.sav_config = NULL;
1052         }
1053         spa->spa_spares.sav_count = 0;
1054 
1055         for (i = 0; i < spa->spa_l2cache.sav_count; i++)
1056                 vdev_free(spa->spa_l2cache.sav_vdevs[i]);
1057         if (spa->spa_l2cache.sav_vdevs) {
1058                 kmem_free(spa->spa_l2cache.sav_vdevs,
1059                     spa->spa_l2cache.sav_count * sizeof (void *));
1060                 spa->spa_l2cache.sav_vdevs = NULL;
1061         }
1062         if (spa->spa_l2cache.sav_config) {
1063                 nvlist_free(spa->spa_l2cache.sav_config);
1064                 spa->spa_l2cache.sav_config = NULL;
1065         }
1066         spa->spa_l2cache.sav_count = 0;
1067 
1068         spa->spa_async_suspended = 0;
1069 
1070         if (spa->spa_comment != NULL) {
1071                 spa_strfree(spa->spa_comment);
1072                 spa->spa_comment = NULL;
1073         }
1074 
1075         spa_config_exit(spa, SCL_ALL, FTAG);
1076 }
1077 
1078 /*
1079  * Load (or re-load) the current list of vdevs describing the active spares for
1080  * this pool.  When this is called, we have some form of basic information in
1081  * 'spa_spares.sav_config'.  We parse this into vdevs, try to open them, and
1082  * then re-generate a more complete list including status information.
1083  */
1084 static void
1085 spa_load_spares(spa_t *spa)
1086 {
1087         nvlist_t **spares;
1088         uint_t nspares;
1089         int i;
1090         vdev_t *vd, *tvd;
1091 
1092         ASSERT(spa_config_held(spa, SCL_ALL, RW_WRITER) == SCL_ALL);
1093 
1094         /*


1770          * If every disk has been moved to the new pool, or if we never
1771          * even attempted to look at them, then we split them off for
1772          * good.
1773          */
1774         if (!attempt_reopen || gcount == extracted) {
1775                 for (i = 0; i < gcount; i++)
1776                         if (vd[i] != NULL)
1777                                 vdev_split(vd[i]);
1778                 vdev_reopen(spa->spa_root_vdev);
1779         }
1780 
1781         kmem_free(vd, gcount * sizeof (vdev_t *));
1782 }
1783 
1784 static int
1785 spa_load(spa_t *spa, spa_load_state_t state, spa_import_type_t type,
1786     boolean_t mosconfig)
1787 {
1788         nvlist_t *config = spa->spa_config;
1789         char *ereport = FM_EREPORT_ZFS_POOL;
1790         char *comment;
1791         int error;
1792         uint64_t pool_guid;
1793         nvlist_t *nvl;
1794 
1795         if (nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_GUID, &pool_guid))
1796                 return (EINVAL);
1797 
1798         ASSERT(spa->spa_comment == NULL);
1799         if (nvlist_lookup_string(config, ZPOOL_CONFIG_COMMENT, &comment) == 0)
1800                 spa->spa_comment = spa_strdup(comment);
1801 
1802         /*
1803          * Versioning wasn't explicitly added to the label until later, so if
1804          * it's not present treat it as the initial version.
1805          */
1806         if (nvlist_lookup_uint64(config, ZPOOL_CONFIG_VERSION,
1807             &spa->spa_ubsync.ub_version) != 0)
1808                 spa->spa_ubsync.ub_version = SPA_VERSION_INITIAL;
1809 
1810         (void) nvlist_lookup_uint64(config, ZPOOL_CONFIG_POOL_TXG,
1811             &spa->spa_config_txg);
1812 
1813         if ((state == SPA_LOAD_IMPORT || state == SPA_LOAD_TRYIMPORT) &&
1814             spa_guid_exists(pool_guid, 0)) {
1815                 error = EEXIST;
1816         } else {
1817                 spa->spa_config_guid = pool_guid;
1818 
1819                 if (nvlist_lookup_nvlist(config, ZPOOL_CONFIG_SPLIT,
1820                     &nvl) == 0) {
1821                         VERIFY(nvlist_dup(nvl, &spa->spa_config_splitting,


5389                                 spa->spa_uberblock.ub_version = intval;
5390                                 vdev_config_dirty(spa->spa_root_vdev);
5391                         }
5392                         break;
5393 
5394                 case ZPOOL_PROP_ALTROOT:
5395                         /*
5396                          * 'altroot' is a non-persistent property. It should
5397                          * have been set temporarily at creation or import time.
5398                          */
5399                         ASSERT(spa->spa_root != NULL);
5400                         break;
5401 
5402                 case ZPOOL_PROP_READONLY:
5403                 case ZPOOL_PROP_CACHEFILE:
5404                         /*
5405                          * 'readonly' and 'cachefile' are also non-persisitent
5406                          * properties.
5407                          */
5408                         break;
5409                 case ZPOOL_PROP_COMMENT:
5410                         VERIFY(nvpair_value_string(elem, &strval) == 0);
5411                         if (spa->spa_comment != NULL)
5412                                 spa_strfree(spa->spa_comment);
5413                         spa->spa_comment = spa_strdup(strval);
5414                         /*
5415                          * We need to dirty the configuration on all the vdevs
5416                          * so that their labels get updated.  It's unnecessary
5417                          * to do this for pool creation since the vdev's
5418                          * configuratoin has already been dirtied.
5419                          */
5420                         if (tx->tx_txg != TXG_INITIAL)
5421                                 vdev_config_dirty(spa->spa_root_vdev);
5422                         break;
5423                 default:
5424                         /*
5425                          * Set pool property values in the poolprops mos object.
5426                          */
5427                         if (spa->spa_pool_props_object == 0) {
5428                                 VERIFY((spa->spa_pool_props_object =
5429                                     zap_create(mos, DMU_OT_POOL_PROPS,
5430                                     DMU_OT_NONE, 0, tx)) > 0);
5431 
5432                                 VERIFY(zap_update(mos,
5433                                     DMU_POOL_DIRECTORY_OBJECT, DMU_POOL_PROPS,
5434                                     8, 1, &spa->spa_pool_props_object, tx)
5435                                     == 0);
5436                         }
5437 
5438                         /* normalize the property name */
5439                         propname = zpool_prop_to_name(prop);
5440                         proptype = zpool_prop_get_type(prop);
5441 
5442                         if (nvpair_type(elem) == DATA_TYPE_STRING) {