X-Git-Url: https://git.camperquake.de/gitweb.cgi?a=blobdiff_plain;f=lib%2Flibzfs%2Flibzfs_dataset.c;h=244b687eddd5895d9232b124d50c79e6c4b1afac;hb=fb5c53ea65b75c67c23f90ebbbb1134a5bb6c140;hp=8c463cd683725ff258d3f35a468a9551e4639c62;hpb=e956d6510699b0c1aa757b1fb0c1ee9feb7419f7;p=zfs.git diff --git a/lib/libzfs/libzfs_dataset.c b/lib/libzfs/libzfs_dataset.c index 8c463cd..244b687 100644 --- a/lib/libzfs/libzfs_dataset.c +++ b/lib/libzfs/libzfs_dataset.c @@ -21,9 +21,10 @@ /* * Copyright (c) 2005, 2010, Oracle and/or its affiliates. All rights reserved. - * Copyright (c) 2010 Nexenta Systems, Inc. All rights reserved. * Copyright (c) 2012 by Delphix. All rights reserved. + * Copyright (c) 2012 DEY Storage Systems, Inc. All rights reserved. * Copyright (c) 2012 Pawel Jakub Dawidek . + * Copyright 2012 Nexenta Systems, Inc. All rights reserved. */ #include @@ -628,12 +629,15 @@ libzfs_mnttab_init(libzfs_handle_t *hdl) sizeof (mnttab_node_t), offsetof(mnttab_node_t, mtn_node)); } -void +int libzfs_mnttab_update(libzfs_handle_t *hdl) { struct mnttab entry; - rewind(hdl->libzfs_mnttab); + /* Reopen MNTTAB to prevent reading stale data from open file */ + if (freopen(MNTTAB, "r", hdl->libzfs_mnttab) == NULL) + return (ENOENT); + while (getmntent(hdl->libzfs_mnttab, &entry) == 0) { mnttab_node_t *mtn; @@ -646,6 +650,8 @@ libzfs_mnttab_update(libzfs_handle_t *hdl) mtn->mtn_mt.mnt_mntopts = zfs_strdup(hdl, entry.mnt_mntopts); avl_add(&hdl->libzfs_mnttab_cache, mtn); } + + return (0); } void @@ -676,13 +682,18 @@ libzfs_mnttab_find(libzfs_handle_t *hdl, const char *fsname, { mnttab_node_t find; mnttab_node_t *mtn; + int error; if (!hdl->libzfs_mnttab_enable) { struct mnttab srch = { 0 }; if (avl_numnodes(&hdl->libzfs_mnttab_cache)) libzfs_mnttab_fini(hdl); - rewind(hdl->libzfs_mnttab); + + /* Reopen MNTTAB to prevent reading stale data from open file */ + if (freopen(MNTTAB, "r", hdl->libzfs_mnttab) == NULL) + return (ENOENT); + srch.mnt_special = (char *)fsname; srch.mnt_fstype = MNTTYPE_ZFS; if (getmntany(hdl->libzfs_mnttab, entry, &srch) == 0) @@ -692,7 +703,8 @@ libzfs_mnttab_find(libzfs_handle_t *hdl, const char *fsname, } if (avl_numnodes(&hdl->libzfs_mnttab_cache) == 0) - libzfs_mnttab_update(hdl); + if ((error = libzfs_mnttab_update(hdl)) != 0) + return (error); find.mtn_mt.mnt_special = (char *)fsname; mtn = avl_find(&hdl->libzfs_mnttab_cache, &find, NULL); @@ -2313,6 +2325,17 @@ zfs_prop_get(zfs_handle_t *zhp, zfs_prop_t prop, char *propbuf, size_t proplen, } break; + case ZFS_PROP_GUID: + /* + * GUIDs are stored as numbers, but they are identifiers. + * We don't want them to be pretty printed, because pretty + * printing mangles the ID into a truncated and useless value. + */ + if (get_numeric_property(zhp, prop, src, &source, &val) != 0) + return (-1); + (void) snprintf(propbuf, proplen, "%llu", (u_longlong_t)val); + break; + default: switch (zfs_prop_get_type(prop)) { case PROP_TYPE_NUMBER: @@ -2520,29 +2543,29 @@ userquota_propname_decode(const char *propname, boolean_t zoned, return (ENOSYS); #endif /* HAVE_IDMAP */ } else { -#ifdef HAVE_IDMAP /* It's a user/group ID (eg "12345"). */ uid_t id; - idmap_rid_t rid; - char *mapdomain; char *end; - id = strtoul(cp, &end, 10); if (*end != '\0') return (EINVAL); if (id > MAXUID) { +#ifdef HAVE_IDMAP /* It's an ephemeral ID. */ + idmap_rid_t rid; + char *mapdomain; + if (idmap_id_to_numeric_domain_rid(id, isuser, &mapdomain, &rid) != 0) return (ENOENT); (void) strlcpy(domain, mapdomain, domainlen); *ridp = rid; +#else + return (ENOSYS); +#endif /* HAVE_IDMAP */ } else { *ridp = id; } -#else - return (ENOSYS); -#endif /* HAVE_IDMAP */ } return (0); @@ -3688,7 +3711,7 @@ zfs_rollback(zfs_handle_t *zhp, zfs_handle_t *snap, boolean_t force) zhp->zfs_type == ZFS_TYPE_VOLUME); /* - * Destroy all recent snapshots and its dependends. + * Destroy all recent snapshots and their dependents. */ cb.cb_force = force; cb.cb_target = snap->zfs_name; @@ -4004,6 +4027,14 @@ zvol_create_link_common(libzfs_handle_t *hdl, const char *dataset, int ifexists) */ return (0); + case ENODEV: + /* + * snapdev set to hidden : + * device creation was not permitted (see zvol.c) + * ignore error quietly + */ + return (0); + case ENOENT: /* * Dataset does not exist in the kernel. If we @@ -4317,35 +4348,40 @@ zfs_userspace(zfs_handle_t *zhp, zfs_userquota_prop_t type, zfs_userspace_cb_t func, void *arg) { zfs_cmd_t zc = { "\0", "\0", "\0", "\0", 0 }; - int error; zfs_useracct_t buf[100]; + libzfs_handle_t *hdl = zhp->zfs_hdl; + int ret; (void) strlcpy(zc.zc_name, zhp->zfs_name, sizeof (zc.zc_name)); zc.zc_objset_type = type; zc.zc_nvlist_dst = (uintptr_t)buf; - /* CONSTCOND */ - while (1) { + for (;;) { zfs_useracct_t *zua = buf; zc.zc_nvlist_dst_size = sizeof (buf); - error = ioctl(zhp->zfs_hdl->libzfs_fd, - ZFS_IOC_USERSPACE_MANY, &zc); - if (error || zc.zc_nvlist_dst_size == 0) + if (zfs_ioctl(hdl, ZFS_IOC_USERSPACE_MANY, &zc) != 0) { + char errbuf[ZFS_MAXNAMELEN + 32]; + + (void) snprintf(errbuf, sizeof (errbuf), + dgettext(TEXT_DOMAIN, + "cannot get used/quota for %s"), zc.zc_name); + return (zfs_standard_error_fmt(hdl, errno, errbuf)); + } + if (zc.zc_nvlist_dst_size == 0) break; while (zc.zc_nvlist_dst_size > 0) { - error = func(arg, zua->zu_domain, zua->zu_rid, - zua->zu_space); - if (error != 0) - return (error); + if ((ret = func(arg, zua->zu_domain, zua->zu_rid, + zua->zu_space)) != 0) + return (ret); zua++; zc.zc_nvlist_dst_size -= sizeof (zfs_useracct_t); } } - return (error); + return (0); } int