zfs-fuse/src/lib/libzfs/libzfs_config.c
/*
 * Loads the pool namespace, or re-loads it if the cache has changed.
 */
Loads the pool namespace, or re-loads it if the cache has changed.
Loads the pool namespace or re - loads it if the cache has changed .
static int
namespace_reload(libzfs_handle_t *hdl)
{
	nvlist_t *config;
	config_node_t *cn;
	nvpair_t *elem;
	zfs_cmd_t zc = { 0 };
	void *cookie;
	if (hdl->libzfs_ns_gen == 0) {
		if ((hdl->libzfs_ns_avlpool = uu_avl_pool_create("config_pool",
		    sizeof (config_node_t),
		    offsetof(config_node_t, cn_avl),
		    config_node_compare, UU_DEFAULT)) == NULL)
			return (no_memory(hdl));
		if ((hdl->libzfs_ns_avl = uu_avl_create(hdl->libzfs_ns_avlpool,
		    NULL, UU_DEFAULT)) == NULL)
			return (no_memory(hdl));
	}
	if (zcmd_alloc_dst_nvlist(hdl, &zc, 0) != 0)
		return (-1);
	for (;;) {
		zc.zc_cookie = hdl->libzfs_ns_gen;
		if (ioctl(hdl->libzfs_fd, ZFS_IOC_POOL_CONFIGS, &zc) != 0) {
			switch (errno) {
			case EEXIST:
				zcmd_free_nvlists(&zc);
				return (0);
			case ENOMEM:
				if (zcmd_expand_dst_nvlist(hdl, &zc) != 0) {
					zcmd_free_nvlists(&zc);
					return (-1);
				}
				break;
			default:
				zcmd_free_nvlists(&zc);
				return (zfs_standard_error(hdl, errno,
				    dgettext(TEXT_DOMAIN, "failed to read "
				    "pool configuration")));
			}
		} else {
			hdl->libzfs_ns_gen = zc.zc_cookie;
			break;
		}
	}
	if (zcmd_read_dst_nvlist(hdl, &zc, &config) != 0) {
		zcmd_free_nvlists(&zc);
		return (-1);
	}
	zcmd_free_nvlists(&zc);
	cookie = NULL;
	while ((cn = uu_avl_teardown(hdl->libzfs_ns_avl, &cookie)) != NULL) {
		nvlist_free(cn->cn_config);
		free(cn->cn_name);
		free(cn);
	}
	elem = NULL;
	while ((elem = nvlist_next_nvpair(config, elem)) != NULL) {
		nvlist_t *child;
		uu_avl_index_t where;
		if ((cn = zfs_alloc(hdl, sizeof (config_node_t))) == NULL) {
			nvlist_free(config);
			return (-1);
		}
		if ((cn->cn_name = zfs_strdup(hdl,
		    nvpair_name(elem))) == NULL) {
			free(cn);
			nvlist_free(config);
			return (-1);
		}
		verify(nvpair_value_nvlist(elem, &child) == 0);
		if (nvlist_dup(child, &cn->cn_config, 0) != 0) {
			free(cn->cn_name);
			free(cn);
			nvlist_free(config);
			return (no_memory(hdl));
		}
		verify(uu_avl_find(hdl->libzfs_ns_avl, cn, NULL, &where)
		    == NULL);
		uu_avl_insert(hdl->libzfs_ns_avl, cn, where);
	}
	nvlist_free(config);
	return (0);
}
static int namespace_reload ( libzfs_handle_t * hdl ) { nvlist_t * config ; config_node_t * cn ; nvpair_t * elem ; zfs_cmd_t zc = { 0 } ; void * cookie ; if ( hdl -> libzfs_ns_gen == 0 ) { if ( ( hdl -> libzfs_ns_avlpool = uu_avl_pool_create ( " " , sizeof ( config_node_t ) , offsetof ( config_node_t , cn_avl ) , config_node_compare , UU_DEFAULT ) ) == NULL ) return ( no_memory ( hdl ) ) ; if ( ( hdl -> libzfs_ns_avl = uu_avl_create ( hdl -> libzfs_ns_avlpool , NULL , UU_DEFAULT ) ) == NULL ) return ( no_memory ( hdl ) ) ; } if ( zcmd_alloc_dst_nvlist ( hdl , & zc , 0 ) != 0 ) return ( -1 ) ; for ( ; ; ) { zc . zc_cookie = hdl -> libzfs_ns_gen ; if ( ioctl ( hdl -> libzfs_fd , ZFS_IOC_POOL_CONFIGS , & zc ) != 0 ) { switch ( errno ) { case EEXIST : zcmd_free_nvlists ( & zc ) ; return ( 0 ) ; case ENOMEM : if ( zcmd_expand_dst_nvlist ( hdl , & zc ) != 0 ) { zcmd_free_nvlists ( & zc ) ; return ( -1 ) ; } break ; default : zcmd_free_nvlists ( & zc ) ; return ( zfs_standard_error ( hdl , errno , dgettext ( TEXT_DOMAIN , " " " " ) ) ) ; } } else { hdl -> libzfs_ns_gen = zc . zc_cookie ; break ; } } if ( zcmd_read_dst_nvlist ( hdl , & zc , & config ) != 0 ) { zcmd_free_nvlists ( & zc ) ; return ( -1 ) ; } zcmd_free_nvlists ( & zc ) ; cookie = NULL ; while ( ( cn = uu_avl_teardown ( hdl -> libzfs_ns_avl , & cookie ) ) != NULL ) { nvlist_free ( cn -> cn_config ) ; free ( cn -> cn_name ) ; free ( cn ) ; } elem = NULL ; while ( ( elem = nvlist_next_nvpair ( config , elem ) ) != NULL ) { nvlist_t * child ; uu_avl_index_t where ; if ( ( cn = zfs_alloc ( hdl , sizeof ( config_node_t ) ) ) == NULL ) { nvlist_free ( config ) ; return ( -1 ) ; } if ( ( cn -> cn_name = zfs_strdup ( hdl , nvpair_name ( elem ) ) ) == NULL ) { free ( cn ) ; nvlist_free ( config ) ; return ( -1 ) ; } verify ( nvpair_value_nvlist ( elem , & child ) == 0 ) ; if ( nvlist_dup ( child , & cn -> cn_config , 0 ) != 0 ) { free ( cn -> cn_name ) ; free ( cn ) ; nvlist_free ( config ) ; return ( no_memory ( hdl ) ) ; } verify ( uu_avl_find ( hdl -> libzfs_ns_avl , cn , NULL , & where ) == NULL ) ; uu_avl_insert ( hdl -> libzfs_ns_avl , cn , where ) ; } nvlist_free ( config ) ; return ( 0 ) ; }
Loads the pool namespace, or re-loads it if the cache has changed.
Loads the pool namespace or re - loads it if the cache has changed .
/*
		 * This is the first time we've accessed the configuration
		 * cache.  Initialize the AVL tree and then fall through to the
		 * common code.
		 */ /*
				 * The namespace hasn't changed.
				 */ /*
	 * Clear out any existing configuration information.
	 */