The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/contrib/openzfs/lib/libzfsbootenv/lzbe_pair.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /*
    2  * This file and its contents are supplied under the terms of the
    3  * Common Development and Distribution License ("CDDL"), version 1.0.
    4  * You may only use this file in accordance with the terms of version
    5  * 1.0 of the CDDL.
    6  *
    7  * A full copy of the text of the CDDL should have accompanied this
    8  * source.  A copy of the CDDL is also available via the Internet at
    9  * http://www.illumos.org/license/CDDL.
   10  */
   11 /*
   12  * Copyright 2020 Toomas Soome <tsoome@me.com>
   13  */
   14 
   15 #include <sys/types.h>
   16 #include <string.h>
   17 #include <libzfs.h>
   18 #include <libzfsbootenv.h>
   19 #include <sys/zfs_bootenv.h>
   20 #include <sys/vdev_impl.h>
   21 
   22 /*
   23  * Get or create nvlist. If key is not NULL, get nvlist from bootenv,
   24  * otherwise return bootenv.
   25  */
   26 int
   27 lzbe_nvlist_get(const char *pool, const char *key, void **ptr)
   28 {
   29         libzfs_handle_t *hdl;
   30         zpool_handle_t *zphdl;
   31         nvlist_t *nv;
   32         int rv = -1;
   33 
   34         if (pool == NULL || *pool == '\0')
   35                 return (rv);
   36 
   37         if ((hdl = libzfs_init()) == NULL) {
   38                 return (rv);
   39         }
   40 
   41         zphdl = zpool_open(hdl, pool);
   42         if (zphdl == NULL) {
   43                 libzfs_fini(hdl);
   44                 return (rv);
   45         }
   46 
   47         rv = zpool_get_bootenv(zphdl, &nv);
   48         if (rv == 0) {
   49                 nvlist_t *nvl, *dup;
   50 
   51                 if (key != NULL) {
   52                         rv = nvlist_lookup_nvlist(nv, key, &nvl);
   53                         if (rv == 0) {
   54                                 rv = nvlist_dup(nvl, &dup, 0);
   55                                 nvlist_free(nv);
   56                                 if (rv == 0)
   57                                         nv = dup;
   58                                 else
   59                                         nv = NULL;
   60                         } else {
   61                                 nvlist_free(nv);
   62                                 rv = nvlist_alloc(&nv, NV_UNIQUE_NAME, 0);
   63                         }
   64                 }
   65                 *ptr = nv;
   66         }
   67 
   68         zpool_close(zphdl);
   69         libzfs_fini(hdl);
   70         return (rv);
   71 }
   72 
   73 int
   74 lzbe_nvlist_set(const char *pool, const char *key, void *ptr)
   75 {
   76         libzfs_handle_t *hdl;
   77         zpool_handle_t *zphdl;
   78         nvlist_t *nv;
   79         uint64_t version;
   80         int rv = -1;
   81 
   82         if (pool == NULL || *pool == '\0')
   83                 return (rv);
   84 
   85         if ((hdl = libzfs_init()) == NULL) {
   86                 return (rv);
   87         }
   88 
   89         zphdl = zpool_open(hdl, pool);
   90         if (zphdl == NULL) {
   91                 libzfs_fini(hdl);
   92                 return (rv);
   93         }
   94 
   95         if (key != NULL) {
   96                 rv = zpool_get_bootenv(zphdl, &nv);
   97                 if (rv == 0) {
   98                         /*
   99                          * We got the nvlist, check for version.
  100                          * if version is missing or is not VB_NVLIST,
  101                          * create new list.
  102                          */
  103                         rv = nvlist_lookup_uint64(nv, BOOTENV_VERSION,
  104                             &version);
  105                         if (rv != 0 || version != VB_NVLIST) {
  106                                 /* Drop this nvlist */
  107                                 fnvlist_free(nv);
  108                                 /* Create and prepare new nvlist */
  109                                 nv = fnvlist_alloc();
  110                                 fnvlist_add_uint64(nv, BOOTENV_VERSION,
  111                                     VB_NVLIST);
  112                         }
  113                         rv = nvlist_add_nvlist(nv, key, ptr);
  114                         if (rv == 0)
  115                                 rv = zpool_set_bootenv(zphdl, nv);
  116                         nvlist_free(nv);
  117                 }
  118         } else {
  119                 rv = zpool_set_bootenv(zphdl, ptr);
  120         }
  121 
  122         zpool_close(zphdl);
  123         libzfs_fini(hdl);
  124         return (rv);
  125 }
  126 
  127 /*
  128  * free nvlist we got via lzbe_nvlist_get()
  129  */
  130 void
  131 lzbe_nvlist_free(void *ptr)
  132 {
  133         nvlist_free(ptr);
  134 }
  135 
  136 static const char *typenames[] = {
  137         "DATA_TYPE_UNKNOWN",
  138         "DATA_TYPE_BOOLEAN",
  139         "DATA_TYPE_BYTE",
  140         "DATA_TYPE_INT16",
  141         "DATA_TYPE_UINT16",
  142         "DATA_TYPE_INT32",
  143         "DATA_TYPE_UINT32",
  144         "DATA_TYPE_INT64",
  145         "DATA_TYPE_UINT64",
  146         "DATA_TYPE_STRING",
  147         "DATA_TYPE_BYTE_ARRAY",
  148         "DATA_TYPE_INT16_ARRAY",
  149         "DATA_TYPE_UINT16_ARRAY",
  150         "DATA_TYPE_INT32_ARRAY",
  151         "DATA_TYPE_UINT32_ARRAY",
  152         "DATA_TYPE_INT64_ARRAY",
  153         "DATA_TYPE_UINT64_ARRAY",
  154         "DATA_TYPE_STRING_ARRAY",
  155         "DATA_TYPE_HRTIME",
  156         "DATA_TYPE_NVLIST",
  157         "DATA_TYPE_NVLIST_ARRAY",
  158         "DATA_TYPE_BOOLEAN_VALUE",
  159         "DATA_TYPE_INT8",
  160         "DATA_TYPE_UINT8",
  161         "DATA_TYPE_BOOLEAN_ARRAY",
  162         "DATA_TYPE_INT8_ARRAY",
  163         "DATA_TYPE_UINT8_ARRAY"
  164 };
  165 
  166 static int
  167 nvpair_type_from_name(const char *name)
  168 {
  169         unsigned i;
  170 
  171         for (i = 0; i < ARRAY_SIZE(typenames); i++) {
  172                 if (strcmp(name, typenames[i]) == 0)
  173                         return (i);
  174         }
  175         return (0);
  176 }
  177 
  178 /*
  179  * Add pair defined by key, type and value into nvlist.
  180  */
  181 int
  182 lzbe_add_pair(void *ptr, const char *key, const char *type, void *value,
  183     size_t size)
  184 {
  185         nvlist_t *nv = ptr;
  186         data_type_t dt;
  187         int rv = 0;
  188 
  189         if (ptr == NULL || key == NULL || value == NULL)
  190                 return (rv);
  191 
  192         if (type == NULL)
  193                 type = "DATA_TYPE_STRING";
  194         dt = nvpair_type_from_name(type);
  195         if (dt == DATA_TYPE_UNKNOWN)
  196                 return (EINVAL);
  197 
  198         switch (dt) {
  199         case DATA_TYPE_BYTE:
  200                 if (size != sizeof (uint8_t)) {
  201                         rv = EINVAL;
  202                         break;
  203                 }
  204                 rv = nvlist_add_byte(nv, key, *(uint8_t *)value);
  205                 break;
  206 
  207         case DATA_TYPE_INT16:
  208                 if (size != sizeof (int16_t)) {
  209                         rv = EINVAL;
  210                         break;
  211                 }
  212                 rv = nvlist_add_int16(nv, key, *(int16_t *)value);
  213                 break;
  214 
  215         case DATA_TYPE_UINT16:
  216                 if (size != sizeof (uint16_t)) {
  217                         rv = EINVAL;
  218                         break;
  219                 }
  220                 rv = nvlist_add_uint16(nv, key, *(uint16_t *)value);
  221                 break;
  222 
  223         case DATA_TYPE_INT32:
  224                 if (size != sizeof (int32_t)) {
  225                         rv = EINVAL;
  226                         break;
  227                 }
  228                 rv = nvlist_add_int32(nv, key, *(int32_t *)value);
  229                 break;
  230 
  231         case DATA_TYPE_UINT32:
  232                 if (size != sizeof (uint32_t)) {
  233                         rv = EINVAL;
  234                         break;
  235                 }
  236                 rv = nvlist_add_uint32(nv, key, *(uint32_t *)value);
  237                 break;
  238 
  239         case DATA_TYPE_INT64:
  240                 if (size != sizeof (int64_t)) {
  241                         rv = EINVAL;
  242                         break;
  243                 }
  244                 rv = nvlist_add_int64(nv, key, *(int64_t *)value);
  245                 break;
  246 
  247         case DATA_TYPE_UINT64:
  248                 if (size != sizeof (uint64_t)) {
  249                         rv = EINVAL;
  250                         break;
  251                 }
  252                 rv = nvlist_add_uint64(nv, key, *(uint64_t *)value);
  253                 break;
  254 
  255         case DATA_TYPE_STRING:
  256                 rv = nvlist_add_string(nv, key, value);
  257                 break;
  258 
  259         case DATA_TYPE_BYTE_ARRAY:
  260                 rv = nvlist_add_byte_array(nv, key, value, size);
  261                 break;
  262 
  263         case DATA_TYPE_INT16_ARRAY:
  264                 rv = nvlist_add_int16_array(nv, key, value, size);
  265                 break;
  266 
  267         case DATA_TYPE_UINT16_ARRAY:
  268                 rv = nvlist_add_uint16_array(nv, key, value, size);
  269                 break;
  270 
  271         case DATA_TYPE_INT32_ARRAY:
  272                 rv = nvlist_add_int32_array(nv, key, value, size);
  273                 break;
  274 
  275         case DATA_TYPE_UINT32_ARRAY:
  276                 rv = nvlist_add_uint32_array(nv, key, value, size);
  277                 break;
  278 
  279         case DATA_TYPE_INT64_ARRAY:
  280                 rv = nvlist_add_int64_array(nv, key, value, size);
  281                 break;
  282 
  283         case DATA_TYPE_UINT64_ARRAY:
  284                 rv = nvlist_add_uint64_array(nv, key, value, size);
  285                 break;
  286 
  287         case DATA_TYPE_STRING_ARRAY:
  288                 rv = nvlist_add_string_array(nv, key, value, size);
  289                 break;
  290 
  291         case DATA_TYPE_NVLIST:
  292                 rv = nvlist_add_nvlist(nv, key, (nvlist_t *)value);
  293                 break;
  294 
  295         case DATA_TYPE_NVLIST_ARRAY:
  296                 rv = nvlist_add_nvlist_array(nv, key, (const nvlist_t **)value,
  297                     size);
  298                 break;
  299 
  300         case DATA_TYPE_BOOLEAN_VALUE:
  301                 if (size != sizeof (boolean_t)) {
  302                         rv = EINVAL;
  303                         break;
  304                 }
  305                 rv = nvlist_add_boolean_value(nv, key, *(boolean_t *)value);
  306                 break;
  307 
  308         case DATA_TYPE_INT8:
  309                 if (size != sizeof (int8_t)) {
  310                         rv = EINVAL;
  311                         break;
  312                 }
  313                 rv = nvlist_add_int8(nv, key, *(int8_t *)value);
  314                 break;
  315 
  316         case DATA_TYPE_UINT8:
  317                 if (size != sizeof (uint8_t)) {
  318                         rv = EINVAL;
  319                         break;
  320                 }
  321                 rv = nvlist_add_uint8(nv, key, *(uint8_t *)value);
  322                 break;
  323 
  324         case DATA_TYPE_BOOLEAN_ARRAY:
  325                 rv = nvlist_add_boolean_array(nv, key, value, size);
  326                 break;
  327 
  328         case DATA_TYPE_INT8_ARRAY:
  329                 rv = nvlist_add_int8_array(nv, key, value, size);
  330                 break;
  331 
  332         case DATA_TYPE_UINT8_ARRAY:
  333                 rv = nvlist_add_uint8_array(nv, key, value, size);
  334                 break;
  335 
  336         default:
  337                 return (ENOTSUP);
  338         }
  339 
  340         return (rv);
  341 }
  342 
  343 int
  344 lzbe_remove_pair(void *ptr, const char *key)
  345 {
  346 
  347         return (nvlist_remove_all(ptr, key));
  348 }

Cache object: 6b3cc06c3bca0aaf2a36e8d667be122b


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.