int snapshot_release(char *volname, char *snapname, char *jname, boolean_t recursive) { zfs_handle_t *zhp; char *p; int rv = 0; if ((zhp = zfs_open(zlibh, volname, ZFS_TYPE_DATASET)) == 0) { NDMP_LOG(LOG_ERR, "Cannot open volume %s", volname); return (-1); } p = strchr(snapname, '@') + 1; if (zfs_release(zhp, p, jname, recursive) != 0) { NDMP_LOG(LOG_DEBUG, "Cannot release snapshot %s", p); rv = -1; } if (cleanup_fd != -1) { (void) close(cleanup_fd); cleanup_fd = -1; } zfs_close(zhp); return (rv); }
int sa_zfs_is_shared(sa_handle_t sahandle, char *path) { int ret = 0; char *dataset; zfs_handle_t *handle = NULL; char shareopts[ZFS_MAXPROPLEN]; libzfs_handle_t *libhandle; dataset = get_zfs_dataset((sa_handle_t)sahandle, path, B_FALSE); if (dataset != NULL) { libhandle = libzfs_init(); if (libhandle != NULL) { handle = zfs_open(libhandle, dataset, ZFS_TYPE_FILESYSTEM); if (handle != NULL) { if (zfs_prop_get(handle, ZFS_PROP_SHARENFS, shareopts, sizeof (shareopts), NULL, NULL, 0, B_FALSE) == 0 && strcmp(shareopts, "off") != 0) { ret = 1; /* it is shared */ } zfs_close(handle); } libzfs_fini(libhandle); } free(dataset); } return (ret); }
/* * Check if the volume type is snapshot volume */ boolean_t fs_is_chkpntvol(char *path) { zfs_handle_t *zhp; char vol[ZFS_MAXNAMELEN]; if (!path || !*path) return (FALSE); if (get_zfsvolname(vol, sizeof (vol), path) == -1) return (FALSE); (void) mutex_lock(&zlib_mtx); if ((zhp = zfs_open(zlibh, vol, ZFS_TYPE_DATASET)) == NULL) { (void) mutex_unlock(&zlib_mtx); return (FALSE); } if (zfs_get_type(zhp) != ZFS_TYPE_SNAPSHOT) { zfs_close(zhp); (void) mutex_unlock(&zlib_mtx); return (FALSE); } zfs_close(zhp); (void) mutex_unlock(&zlib_mtx); return (TRUE); }
static int fsi_zfs_open(fsi_file_t *ffi, char *filename) { char *fsi_bootstring; uint64_t *fmax; uint64_t *fpos; int rc; zfs_ffi = ffi; fmax = fsig_filemax(ffi); fpos = fsig_filepos(ffi); rc = zfs_open(filename); if (rc != 1) { return (rc); } *fmax = filemax; *fpos = filepos; if (bootstring == NULL) { rc = asprintf(&bootstring, "zfs-bootfs=%s/%"PRIu64",bootpath='%s'", current_rootpool, current_bootfs_obj, current_bootpath); if (rc == -1) { return (rc); } fsi_bootstring = fsi_bootstring_alloc(ffi->ff_fsi, strlen(bootstring) + 1); strcpy(fsi_bootstring, bootstring); } return (rc); }
/* * Get the snapshot creation time */ int chkpnt_creationtime_bypattern(char *volname, char *pattern, time_t *tp) { char chk_name[PATH_MAX]; zfs_handle_t *zhp; char *p; if (!volname || !*volname) return (-1); /* Should also return -1 if checkpoint not enabled */ /* Remove the leading slash */ p = volname; while (*p == '/') p++; (void) strlcpy(chk_name, p, PATH_MAX); (void) strlcat(chk_name, "@", PATH_MAX); (void) strlcat(chk_name, pattern, PATH_MAX); (void) mutex_lock(&zlib_mtx); if ((zhp = zfs_open(zlibh, chk_name, ZFS_TYPE_DATASET)) == NULL) { NDMP_LOG(LOG_DEBUG, "chkpnt_creationtime: open %s failed", chk_name); (void) mutex_unlock(&zlib_mtx); return (-1); } *tp = zfs_prop_get_int(zhp, ZFS_PROP_CREATION); zfs_close(zhp); (void) mutex_unlock(&zlib_mtx); return (0); }
/* * This function is best effort. It attempts to load all the keys for the given * filesystem and all of its children. */ int zfs_crypto_attempt_load_keys(libzfs_handle_t *hdl, char *fsname) { int ret; zfs_handle_t *zhp = NULL; loadkey_cbdata_t cb = { 0 }; zhp = zfs_open(hdl, fsname, ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME); if (zhp == NULL) { ret = ENOENT; goto error; } ret = load_keys_cb(zfs_handle_dup(zhp), &cb); if (ret) goto error; (void) printf(gettext("%llu / %llu keys successfully loaded\n"), (u_longlong_t)(cb.cb_numattempted - cb.cb_numfailed), (u_longlong_t)cb.cb_numattempted); if (cb.cb_numfailed != 0) { ret = -1; goto error; } zfs_close(zhp); return (0); error: if (zhp != NULL) zfs_close(zhp); return (ret); }
/* * Put a hold on snapshot */ int snapshot_hold(char *volname, char *snapname, char *jname, boolean_t recursive) { zfs_handle_t *zhp; char *p; if ((zhp = zfs_open(zlibh, volname, ZFS_TYPE_DATASET)) == 0) { NDMP_LOG(LOG_ERR, "Cannot open volume %s.", volname); return (-1); } if (cleanup_fd == -1 && (cleanup_fd = open(ZFS_DEV, O_RDWR|O_EXCL)) < 0) { NDMP_LOG(LOG_ERR, "Cannot open dev %d", errno); zfs_close(zhp); return (-1); } p = strchr(snapname, '@') + 1; if (zfs_hold(zhp, p, jname, recursive, cleanup_fd) != 0) { NDMP_LOG(LOG_ERR, "Cannot hold snapshot %s", p); zfs_close(zhp); return (-1); } zfs_close(zhp); return (0); }
/* Remove a home directory structure */ int rm_homedir(char *dir) { struct stat stbuf; char *nm; if ((stat(dir, &stbuf) != 0) || !S_ISDIR(stbuf.st_mode)) return 0; if (g_zfs == NULL) g_zfs = libzfs_init(); if ((strcmp(stbuf.st_fstype, MNTTYPE_ZFS) == 0) && (g_zfs != NULL) && ((nm = get_mnt_special(dir, stbuf.st_fstype)) != NULL)) { zfs_handle_t *zhp; if ((zhp = zfs_open(g_zfs, nm, ZFS_TYPE_FILESYSTEM)) != NULL) { if ((zfs_unmount(zhp, NULL, 0) == 0) && (zfs_destroy(zhp, B_FALSE) == 0)) { zfs_close(zhp); return 0; } (void) zfs_mount(zhp, NULL, 0); zfs_close(zhp); } } (void) sprintf(cmdbuf, "rm -rf %s", dir); return (system(cmdbuf)); }
int zpool_enable_datasets(zpool_handle_t *zhp, const char *mntopts, int flags) { get_all_cb_t cb = { 0 }; libzfs_handle_t *hdl = zhp->zpool_hdl; zfs_handle_t *zfsp; int i, ret = -1; int *good; /* * Gather all non-snap datasets within the pool. */ if ((zfsp = zfs_open(hdl, zhp->zpool_name, ZFS_TYPE_DATASET)) == NULL) goto out; libzfs_add_handle(&cb, zfsp); if (zfs_iter_filesystems(zfsp, mount_cb, &cb) != 0) goto out; /* * Sort the datasets by mountpoint. */ qsort(cb.cb_handles, cb.cb_used, sizeof (void *), libzfs_dataset_cmp); /* * And mount all the datasets, keeping track of which ones * succeeded or failed. */ if ((good = zfs_alloc(zhp->zpool_hdl, cb.cb_used * sizeof (int))) == NULL) goto out; ret = 0; for (i = 0; i < cb.cb_used; i++) { if (zfs_mount(cb.cb_handles[i], mntopts, flags) != 0) ret = -1; else good[i] = 1; } /* * Then share all the ones that need to be shared. This needs * to be a separate pass in order to avoid excessive reloading * of the configuration. Good should never be NULL since * zfs_alloc is supposed to exit if memory isn't available. */ for (i = 0; i < cb.cb_used; i++) { if (good[i] && zfs_share(cb.cb_handles[i]) != 0) ret = -1; } free(good); out: for (i = 0; i < cb.cb_used; i++) zfs_close(cb.cb_handles[i]); free(cb.cb_handles); return (ret); }
/* * path - path of the dataset * count - return value of the number of snapshots for the dataset */ int smbd_vss_get_count(const char *path, uint32_t *count) { char dataset[MAXPATHLEN]; libzfs_handle_t *libhd; zfs_handle_t *zfshd; smbd_vss_count_t vss_count; bzero(&vss_count, sizeof (smbd_vss_count_t)); *count = 0; if (smb_getdataset(path, dataset, MAXPATHLEN) != 0) return (-1); if ((libhd = libzfs_init()) == NULL) return (-1); if ((zfshd = zfs_open(libhd, dataset, ZFS_TYPE_DATASET)) == NULL) { libzfs_fini(libhd); return (-1); } (void) zfs_iter_snapshots(zfshd, smbd_vss_iterate_count, (void *)&vss_count); if (vss_count.vc_count > SMBD_VSS_SNAPSHOT_MAX) vss_count.vc_count = SMBD_VSS_SNAPSHOT_MAX; *count = vss_count.vc_count; zfs_close(zfshd); libzfs_fini(libhd); return (0); }
/* Remove a home directory structure */ int rm_homedir(char *dir, int flags) { struct stat stbuf; char *nm, *rp; rp = realpath(dir, NULL); if (rp && (strcmp(rp, "/") == 0)) { return (0); } if ((stat(dir, &stbuf) != 0) || !S_ISDIR(stbuf.st_mode)) return (0); if ((strcmp(stbuf.st_fstype, MNTTYPE_ZFS) == 0) && (flags & MANAGE_ZFS)) { if (g_zfs == NULL) g_zfs = libzfs_init(); if (g_zfs == NULL) { errmsg(M_OOPS, "libzfs_init failure", strerror(errno)); return (EX_HOMEDIR); } if ((nm = get_mnt_special(dir, stbuf.st_fstype)) != NULL) { zfs_handle_t *zhp; if ((zhp = zfs_open(g_zfs, nm, ZFS_TYPE_FILESYSTEM)) != NULL) { if ((zfs_unmount(zhp, NULL, 0) == 0) && (zfs_destroy(zhp, B_FALSE) == 0)) { zfs_close(zhp); libzfs_fini(g_zfs); g_zfs = NULL; return (0); } errmsg(M_OOPS, "destroy the home directory", libzfs_error_description(g_zfs)); (void) zfs_mount(zhp, NULL, 0); zfs_close(zhp); libzfs_fini(g_zfs); g_zfs = NULL; return (EX_HOMEDIR); } } } (void) sprintf(cmdbuf, "rm -rf %s", dir); if (g_zfs != NULL) { libzfs_fini(g_zfs); g_zfs = NULL; } return (system(cmdbuf)); }
/* * Sets the share properties on a ZFS share. For now, this method sets only * the "sharesmb" property. * * This method includes building a comma seperated name-value string to be * set on the "sharesmb" property of a ZFS share. This name-value string is * build in 2 steps: * - New property values given as name-value pair are set first. * - Existing optionset properties, which are not part of the new properties * passed in step 1, are appended to the newly set properties. */ int sa_zfs_setprop(sa_handle_t handle, char *path, nvlist_t *nvl) { zfs_handle_t *z_fs; libzfs_handle_t *z_lib; char sharesmb_val[MAXPATHLEN]; char *dataset, *lastcomma; if (nvlist_empty(nvl)) return (0); if ((handle == NULL) || (path == NULL)) return (-1); if ((dataset = get_zfs_dataset(handle, path, B_FALSE)) == NULL) return (-1); if ((z_lib = libzfs_init()) == NULL) { free(dataset); return (-1); } z_fs = zfs_open(z_lib, dataset, ZFS_TYPE_DATASET); if (z_fs == NULL) { free(dataset); libzfs_fini(z_lib); return (-1); } bzero(sharesmb_val, MAXPATHLEN); if (sa_zfs_sprintf_new_prop(nvl, sharesmb_val) != 0) { free(dataset); zfs_close(z_fs); libzfs_fini(z_lib); return (-1); } if (sa_zfs_sprintf_existing_prop(z_fs, sharesmb_val) != 0) { free(dataset); zfs_close(z_fs); libzfs_fini(z_lib); return (-1); } lastcomma = strrchr(sharesmb_val, ','); if ((lastcomma != NULL) && (lastcomma[1] == '\0')) *lastcomma = '\0'; (void) zfs_prop_set(z_fs, zfs_prop_to_name(ZFS_PROP_SHARESMB), sharesmb_val); free(dataset); zfs_close(z_fs); libzfs_fini(z_lib); return (0); }
/* * Read the server config as properties associated with the dataset. * Missing entries as not treated error and are simply skipped. */ int zfs_read_ldd(char *ds, struct lustre_disk_data *ldd) { zfs_handle_t *zhp; int ret = EINVAL; if (osd_check_zfs_setup() == 0) return EINVAL; zhp = zfs_open(g_zfs, ds, ZFS_TYPE_FILESYSTEM); if (zhp == NULL) goto out; ret = zfs_get_prop_int(zhp, LDD_VERSION_PROP, &ldd->ldd_config_ver); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_int(zhp, LDD_FLAGS_PROP, &ldd->ldd_flags); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_int(zhp, LDD_INDEX_PROP, &ldd->ldd_svindex); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_str(zhp, LDD_FSNAME_PROP, ldd->ldd_fsname); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_str(zhp, LDD_SVNAME_PROP, ldd->ldd_svname); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_str(zhp, LDD_UUID_PROP, (char *)ldd->ldd_uuid); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_str(zhp, LDD_USERDATA_PROP, ldd->ldd_userdata); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_str(zhp, LDD_MOUNTOPTS_PROP, ldd->ldd_mount_opts); if (ret && (ret != ENOENT)) goto out_close; ret = zfs_get_prop_str(zhp, LDD_PARAMS_PROP, ldd->ldd_params); if (ret && (ret != ENOENT)) goto out_close; ldd->ldd_mount_type = LDD_MT_ZFS; ret = 0; out_close: zfs_close(zhp); out: return ret; }
/* * path - path of the dataset for the operation * gmttoken - the @GMT token to be looked up * toktime - time_t used if gmttoken == NULL * snapname - the snapshot name to be returned [MAXPATHLEN] * * Here we are going to get the snapshot name from the @GMT token * The snapname returned by ZFS is : <dataset name>@<snapshot name> * So we are going to make sure there is the @ symbol in * the right place and then just return the snapshot name */ int smbd_vss_map_gmttoken(const char *path, char *gmttoken, time_t toktime, char *snapname) { char dataset[MAXPATHLEN]; libzfs_handle_t *libhd; zfs_handle_t *zfshd; smbd_vss_map_gmttoken_t vss_map_gmttoken; char *zsnap; const char *lsnap; struct tm tm; if (gmttoken != NULL && *gmttoken == '@' && strptime(gmttoken, smbd_vss_gmttoken_fmt, &tm) != NULL) { toktime = timegm(&tm); } vss_map_gmttoken.mg_snaptime = toktime; vss_map_gmttoken.mg_snapname = snapname; *snapname = '\0'; if (smb_getdataset(path, dataset, MAXPATHLEN) != 0) return (-1); if ((libhd = libzfs_init()) == NULL) return (-1); if ((zfshd = zfs_open(libhd, dataset, ZFS_TYPE_DATASET)) == NULL) { libzfs_fini(libhd); return (-1); } (void) zfs_iter_snapshots(zfshd, smbd_vss_iterate_map_gmttoken, (void *)&vss_map_gmttoken); /* compare the zfs snapshot name and the local snap name */ zsnap = snapname; lsnap = dataset; while ((*lsnap != '\0') && (*zsnap != '\0') && (*lsnap == *zsnap)) { zsnap++; lsnap++; } /* Now we should be passed the dataset name */ if ((*zsnap == '@') && (*lsnap == '\0')) { zsnap++; (void) strlcpy(snapname, zsnap, MAXPATHLEN); } else { *snapname = '\0'; } zfs_close(zfshd); libzfs_fini(libhd); return (0); }
/** * Create the zpool * @param p_libzfshd: libzfs handle * @param psz_zpool: zpool name * @param pnv_root: the root tree of vdev * @param pnv_props: the tree of properties (can be NULL) * @param pnv_fsprops: the tree of the file system properties (can be NULL) * @param ppsz_error: the error message if any * @return 0 in case of error, the error code overwise */ int libzfs_zpool_create(libzfs_handle_t *p_libzfshd, const char* psz_zpool, nvlist_t *pnv_root, nvlist_t *pnv_props, nvlist_t *pnv_fsprops, const char **ppsz_error) { int i_error; char *psz_altroot; /* Check the zpool name */ if(libzfs_zpool_name_valid(psz_zpool, ppsz_error)) return EINVAL; /** Check the properties TODO: zpool_valid_proplist and zfs_valid_proplist */ if((i_error = spa_create(psz_zpool, pnv_root, pnv_props, "libzfswrap_zpool_create", pnv_fsprops))) { switch(i_error) { case EBUSY: *ppsz_error = "one or more vdevs refer to the same device"; break; case EOVERFLOW: *ppsz_error = "one or more devices is less than the minimum size (64Mo)"; break; case ENOSPC: *ppsz_error = "one or more devices is out of space"; break; case ENOTBLK: *ppsz_error = "cache device must be a disk or disk slice"; break; case EEXIST: *ppsz_error = "the pool already exist"; break; default: *ppsz_error = "unable to create the spa"; } return i_error; } /* If this is an alternate root pool, then automatically set the mountpoint to be '/' */ if(nvlist_lookup_string(pnv_props, zpool_prop_to_name(ZPOOL_PROP_ALTROOT), &psz_altroot) == 0) { zfs_handle_t *p_zhd; assert((p_zhd = zfs_open(p_libzfshd, psz_zpool, ZFS_TYPE_DATASET)) != NULL); assert(zfs_prop_set(p_zhd, zfs_prop_to_name(ZFS_PROP_MOUNTPOINT), "/") == 0); zfs_close(p_zhd); } return 0; }
/* * Function: be_get_zone_be_list * Description: Finds all the BEs for this zone on the system. * Parameters: * zone_be_name - The name of the BE to look up. * zone_be_container_ds - The dataset for the zone. * zbe_nodes - A reference pointer to the list of BEs. The list * structure will be allocated here and must * be freed by a call to be_free_list. If there are no * BEs found on the system this reference will be * set to NULL. * Return: * BE_SUCCESS - Success * be_errno_t - Failure * Scope: * Semi-private (library wide use only) */ int be_get_zone_be_list( /* LINTED */ char *zone_be_name, char *zone_be_container_ds, be_node_list_t **zbe_nodes) { zfs_handle_t *zhp = NULL; list_callback_data_t cb = { 0 }; int ret = BE_SUCCESS; if (zbe_nodes == NULL) return (BE_ERR_INVAL); if (!zfs_dataset_exists(g_zfs, zone_be_container_ds, ZFS_TYPE_FILESYSTEM)) { return (BE_ERR_BE_NOENT); } zone_be = B_TRUE; if ((zhp = zfs_open(g_zfs, zone_be_container_ds, ZFS_TYPE_FILESYSTEM)) == NULL) { be_print_err(gettext("be_get_zone_be_list: failed to open " "the zone BE dataset %s: %s\n"), zone_be_container_ds, libzfs_error_description(g_zfs)); ret = zfs_err_to_be_err(g_zfs); goto cleanup; } (void) strcpy(be_container_ds, zone_be_container_ds); if (cb.be_nodes_head == NULL) { if ((cb.be_nodes_head = be_list_alloc(&ret, sizeof (be_node_list_t))) == NULL) { ZFS_CLOSE(zhp); goto cleanup; } cb.be_nodes = cb.be_nodes_head; } if (ret == 0) ret = zfs_iter_filesystems(zhp, be_add_children_callback, &cb); ZFS_CLOSE(zhp); *zbe_nodes = cb.be_nodes_head; cleanup: zone_be = B_FALSE; return (ret); }
int zfs_label_lustre(struct mount_opts *mop) { zfs_handle_t *zhp; int ret; if (osd_check_zfs_setup() == 0) return EINVAL; zhp = zfs_open(g_zfs, mop->mo_source, ZFS_TYPE_FILESYSTEM); if (zhp == NULL) return EINVAL; ret = zfs_set_prop_str(zhp, LDD_SVNAME_PROP, mop->mo_ldd.ldd_svname); zfs_close(zhp); return ret; }
static int zpl_open(struct inode *ip, struct file *filp) { cred_t *cr = CRED(); int error; error = generic_file_open(ip, filp); if (error) return (error); crhold(cr); error = -zfs_open(ip, filp->f_mode, filp->f_flags, cr); crfree(cr); ASSERT3S(error, <=, 0); return (error); }
/* * Just checking the existance of the given target. Here we check whether * both zfs and iscsitarget aware of the given target/volume. It neither * care about the credentials nor SHAREISCSI properties. */ static char * validate_zfs_iscsitgt(tgt_node_t *x) { char *msg = NULL; char *prop = NULL; char *dataset = NULL; libzfs_handle_t *zh = NULL; zfs_handle_t *zfsh = NULL; tgt_node_t *n = NULL; if (tgt_find_value_str(x, XML_ELEMENT_NAME, &dataset) == False) { xml_rtn_msg(&msg, ERR_SYNTAX_MISSING_NAME); return (msg); } if (((zh = libzfs_init()) == NULL) || ((zfsh = zfs_open(zh, dataset, ZFS_TYPE_DATASET)) == NULL)) { xml_rtn_msg(&msg, ERR_TARG_NOT_FOUND); goto error; } while ((n = tgt_node_next_child(targets_config, XML_ELEMENT_TARG, n)) != NULL) { if (strcmp(n->x_value, dataset) == 0) break; } if (n == NULL) { xml_rtn_msg(&msg, ERR_TARG_NOT_FOUND); goto error; } xml_rtn_msg(&msg, ERR_SUCCESS); error: if (zfsh) zfs_close(zfsh); if (prop) free(prop); if (zh) libzfs_fini(zh); if (dataset) free(dataset); return (msg); }
void Destroy::find(const std::string &root) { zfs_handle_t *hzfs = zfs_open(m_hlib, root.c_str(), ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME); if (!hzfs) { std::cerr << root << ": " << libzfs_error_description(m_hlib) << std::endl; return; } zfs_iter_snapshots(hzfs, B_FALSE, iter_dataset, this); if (m_recursive) { zfs_iter_filesystems(hzfs, iter_dataset, this); } zfs_close(hzfs); }
/* * Destroy the given pool. It is up to the caller to ensure that there are no * datasets left in the pool. */ int zpool_destroy(zpool_handle_t *zhp) { zfs_cmd_t zc = { 0 }; zfs_handle_t *zfp = NULL; libzfs_handle_t *hdl = zhp->zpool_hdl; char msg[1024]; if (zhp->zpool_state == POOL_STATE_ACTIVE && (zfp = zfs_open(zhp->zpool_hdl, zhp->zpool_name, ZFS_TYPE_FILESYSTEM)) == NULL) return (-1); if (zpool_remove_zvol_links(zhp) != NULL) return (-1); (void) strlcpy(zc.zc_name, zhp->zpool_name, sizeof (zc.zc_name)); if (ioctl(zhp->zpool_hdl->libzfs_fd, ZFS_IOC_POOL_DESTROY, &zc) != 0) { (void) snprintf(msg, sizeof (msg), dgettext(TEXT_DOMAIN, "cannot destroy '%s'"), zhp->zpool_name); if (errno == EROFS) { zfs_error_aux(hdl, dgettext(TEXT_DOMAIN, "one or more devices is read only")); (void) zfs_error(hdl, EZFS_BADDEV, msg); } else { (void) zpool_standard_error(hdl, errno, msg); } if (zfp) zfs_close(zfp); return (-1); } if (zfp) { remove_mountpoint(zfp); zfs_close(zfp); } return (0); }
static int zpl_open(struct inode *ip, struct file *filp) { cred_t *cr = CRED(); int error; fstrans_cookie_t cookie; error = generic_file_open(ip, filp); if (error) return (error); crhold(cr); cookie = spl_fstrans_mark(); error = -zfs_open(ip, filp->f_mode, filp->f_flags, cr); spl_fstrans_unmark(cookie); crfree(cr); ASSERT3S(error, <=, 0); return (error); }
static int zvol_cb(const char *dataset, void *data) { libzfs_handle_t *hdl = data; zfs_handle_t *zhp; /* * Ignore snapshots and ignore failures from non-existant datasets. */ if (strchr(dataset, '@') != NULL || (zhp = zfs_open(hdl, dataset, ZFS_TYPE_VOLUME)) == NULL) return (0); if (zfs_unshare_iscsi(zhp) != 0) return (-1); zfs_close(zhp); return (0); }
static char * get_zfs_dataset(sa_handle_impl_t impl_handle, char *path, boolean_t search_mnttab) { size_t i, count = 0; zfs_handle_t **zlist; char *cutpath; zfs_handle_t *handle_from_path; char *ret = NULL; /* * First we optimistically assume that the mount path for the filesystem * is the same as the name of the filesystem (minus some number of * leading slashes). If this is true, then zfs_open should properly open * the filesystem. We duplicate the error checking done later in the * function for consistency. If anything fails, we resort to the * (extremely slow) search of all the filesystems. */ cutpath = path + strspn(path, "/"); assert(impl_handle->zfs_libhandle != NULL); if ((handle_from_path = zfs_open(impl_handle->zfs_libhandle, cutpath, ZFS_TYPE_FILESYSTEM)) != NULL) if ((ret = verify_zfs_handle(handle_from_path, path, search_mnttab)) != NULL) return (ret); /* * Couldn't find a filesystem optimistically, check all the handles we * can. */ get_all_filesystems(impl_handle, &zlist, &count); for (i = 0; i < count; i++) { assert(zlist[i]); if ((ret = verify_zfs_handle(zlist[i], path, search_mnttab)) != NULL) return (ret); } /* Couldn't find a matching dataset */ return (NULL); }
int zfs_iter_clones(zfs_handle_t *zhp, zfs_iter_f func, void *data) { nvlist_t *nvl = zfs_get_clones_nvl(zhp); nvpair_t *pair; if (nvl == NULL) return (0); for (pair = nvlist_next_nvpair(nvl, NULL); pair != NULL; pair = nvlist_next_nvpair(nvl, pair)) { zfs_handle_t *clone = zfs_open(zhp->zfs_hdl, nvpair_name(pair), ZFS_TYPE_FILESYSTEM | ZFS_TYPE_VOLUME); if (clone != NULL) { int err = func(clone, data); if (err != 0) return (err); } } return (0); }
void Destroy::destroy(const std::string &name) { if (m_verbose) std::cout << " " << (m_dry_run ? "would destroy : " : "destroying : ") << name << "\n"; if (m_dry_run) return; zfs_handle_t *hzfs = zfs_open(m_hlib, name.c_str(), ZFS_TYPE_SNAPSHOT); if (!hzfs) { std::cerr << name << ": " << libzfs_error_description(m_hlib) << std::endl; return; } zfs_destroy(hzfs, m_defer ? B_TRUE : B_FALSE); zfs_close(hzfs); }
/* * Insert the backup snapshot name into the path. * * Input: * name: Original path name. * * Output: * name: Original name modified to include a snapshot. * * Returns: * Original name modified to include a snapshot. */ char * tlm_build_snapshot_name(char *name, char *sname, char *jname) { zfs_handle_t *zhp; char *rest; char volname[ZFS_MAXNAMELEN]; char mountpoint[PATH_MAX]; if (get_zfsvolname(volname, ZFS_MAXNAMELEN, name) == -1) goto notzfs; (void) mutex_lock(&zlib_mtx); if ((zlibh == NULL) || (zhp = zfs_open(zlibh, volname, ZFS_TYPE_DATASET)) == NULL) { (void) mutex_unlock(&zlib_mtx); goto notzfs; } if (zfs_prop_get(zhp, ZFS_PROP_MOUNTPOINT, mountpoint, PATH_MAX, NULL, NULL, 0, B_FALSE) != 0) { zfs_close(zhp); (void) mutex_unlock(&zlib_mtx); goto notzfs; } zfs_close(zhp); (void) mutex_unlock(&zlib_mtx); rest = name + strlen(mountpoint); (void) snprintf(sname, TLM_MAX_PATH_NAME, "%s/%s/%s%s", mountpoint, TLM_SNAPSHOT_DIR, jname, rest); return (sname); notzfs: (void) strlcpy(sname, name, TLM_MAX_PATH_NAME); return (sname); }
static int update_zfs_share(sa_share_impl_t impl_share, const char *proto) { sa_handle_impl_t impl_handle = impl_share->handle; zfs_handle_t *zhp; update_cookie_t udata; if (impl_handle->zfs_libhandle == NULL) return (SA_SYSTEM_ERR); assert(impl_share->dataset != NULL); zhp = zfs_open(impl_share->handle->zfs_libhandle, impl_share->dataset, ZFS_TYPE_FILESYSTEM); if (zhp == NULL) return (SA_SYSTEM_ERR); udata.handle = impl_handle; udata.proto = proto; (void) update_zfs_shares_cb(zhp, &udata); return (SA_OK); }
/* * ndmp_has_backup_snapshot * * Returns TRUE if the volume has an active backup snapshot, otherwise, * returns FALSE. * * Parameters: * volname (input) - name of the volume * * Returns: * 0: on success * -1: otherwise */ static int ndmp_has_backup_snapshot(char *volname, char *jobname) { zfs_handle_t *zhp; snap_param_t snp; char chname[ZFS_MAXNAMELEN]; (void) mutex_lock(&zlib_mtx); if ((zhp = zfs_open(zlibh, volname, ZFS_TYPE_DATASET)) == 0) { NDMP_LOG(LOG_ERR, "Cannot open snapshot %s.", volname); (void) mutex_unlock(&zlib_mtx); return (-1); } snp.snp_found = 0; (void) snprintf(chname, ZFS_MAXNAMELEN, "@%s", jobname); snp.snp_name = chname; (void) zfs_iter_snapshots(zhp, B_FALSE, ndmp_has_backup, &snp); zfs_close(zhp); (void) mutex_unlock(&zlib_mtx); return (snp.snp_found); }
static char * get_zfs_property(char *dataset, zfs_prop_t property) { zfs_handle_t *handle = NULL; char shareopts[ZFS_MAXPROPLEN]; libzfs_handle_t *libhandle; libhandle = libzfs_init(); if (libhandle != NULL) { handle = zfs_open(libhandle, dataset, ZFS_TYPE_FILESYSTEM); if (handle != NULL) { if (zfs_prop_get(handle, property, shareopts, sizeof (shareopts), NULL, NULL, 0, B_FALSE) == 0) { zfs_close(handle); libzfs_fini(libhandle); return (strdup(shareopts)); } zfs_close(handle); } libzfs_fini(libhandle); } return (NULL); }