/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License (the "License").
* You may not use this file except in compliance with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2009 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
/*
* Copyright (c) 2012 by Delphix. All rights reserved.
* Copyright (c) 2015 by Syneto S.R.L. All rights reserved.
* Copyright 2016 Nexenta Systems, Inc.
*/
/*
* The pool configuration repository is stored in /etc/zfs/zpool.cache as a
* single packed nvlist. While it would be nice to just read in this
* file from userland, this wouldn't work from a local zone. So we have to have
* a zpool ioctl to return the complete configuration for all pools. In the
* global zone, this will be identical to reading the file and unpacking it in
* userland.
*/
#include <errno.h>
#include <fcntl.h>
#include <stddef.h>
#include <string.h>
#include <unistd.h>
#include <libintl.h>
#include <libuutil.h>
#include "libzfs_impl.h"
typedef struct config_node {
char *cn_name;
/* ARGSUSED */
static int
{
int ret;
if (ret < 0)
return (-1);
else if (ret > 0)
return (1);
else
return (0);
}
void
{
if (hdl->libzfs_ns_avl) {
}
}
if (hdl->libzfs_ns_avlpool) {
}
}
/*
* Loads the pool namespace, or re-loads it if the cache has changed.
*/
static int
{
void *cookie;
if (hdl->libzfs_ns_gen == 0) {
/*
* This is the first time we've accessed the configuration
* cache. Initialize the AVL tree and then fall through to the
* common code.
*/
sizeof (config_node_t),
}
return (-1);
for (;;) {
switch (errno) {
case EEXIST:
/*
* The namespace hasn't changed.
*/
return (0);
case ENOMEM:
return (-1);
}
break;
default:
"pool configuration")));
}
} else {
break;
}
}
return (-1);
}
/*
* Clear out any existing configuration information.
*/
}
return (-1);
}
return (-1);
}
}
== NULL);
}
return (0);
}
/*
* Retrieve the configuration for the given pool. The configuration is a nvlist
* describing the vdevs, as well as the statistics associated with each one.
*/
nvlist_t *
{
if (oldconfig)
return (zhp->zpool_config);
}
/*
* Retrieves a list of enabled features and their refcounts and caches it in
* the pool handle.
*/
nvlist_t *
{
int error;
return (NULL);
}
&features) != 0)
return (NULL);
return (features);
}
/*
* Refresh the vdev statistics associated with the given pool. This is used in
* iostat to show configuration changes and determine the delta from the last
* time the function was called. This function can fail, in case the pool has
* been destroyed.
*/
int
{
int error;
if (zhp->zpool_config_size == 0)
return (-1);
for (;;) {
&zc) == 0) {
/*
* The real error is returned in the zc_cookie field.
*/
break;
}
return (-1);
}
} else {
return (0);
}
}
return (-1);
}
ZPOOL_CONFIG_POOL_TXG, &oldtxg) == 0);
ZPOOL_CONFIG_POOL_TXG, &newtxg) == 0);
} else {
}
}
if (error)
else
return (0);
}
/*
* The following environment variables are undocumented
* and should be used for testing purposes only:
*
* __ZFS_POOL_EXCLUDE - don't iterate over the pools it lists
* __ZFS_POOL_RESTRICT - iterate only over the pools it lists
*
* This function returns B_TRUE if the pool should be skipped
* during iteration.
*/
{
int len;
if (!initialized) {
}
do {
return (B_TRUE);
}
if (NULL == restricted)
return (B_FALSE);
cur = restricted;
do {
return (B_FALSE);
}
return (B_TRUE);
}
/*
* Iterate over all pools in the system.
*/
int
{
int ret;
/*
* If someone makes a recursive call to zpool_iter(), we want to avoid
* refreshing the namespace because that will invalidate the parent
* context. We allow recursive calls, but simply re-use the same
* namespace AVL tree.
*/
return (-1);
hdl->libzfs_pool_iter++;
continue;
hdl->libzfs_pool_iter--;
return (-1);
}
continue;
hdl->libzfs_pool_iter--;
return (ret);
}
}
hdl->libzfs_pool_iter--;
return (0);
}
/*
* Iterate over root datasets, calling the given function for each. The zfs
* handle passed each time must be explicitly closed by the callback.
*/
int
{
int ret;
if (namespace_reload(hdl) != 0)
return (-1);
continue;
continue;
return (ret);
}
return (0);
}