1 /* 2 * CDDL HEADER START 3 * 4 * The contents of this file are subject to the terms of the 5 * Common Development and Distribution License (the "License"). 6 * You may not use this file except in compliance with the License. 7 * 8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE 9 * or http://www.opensolaris.org/os/licensing. 10 * See the License for the specific language governing permissions 11 * and limitations under the License. 12 * 13 * When distributing Covered Code, include this CDDL HEADER in each 14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE. 15 * If applicable, add the following below this CDDL HEADER, with the 16 * fields enclosed by brackets "[]" replaced with your own identifying 17 * information: Portions Copyright [yyyy] [name of copyright owner] 18 * 19 * CDDL HEADER END 20 */ 21 /* 22 * Copyright 2009 Sun Microsystems, Inc. All rights reserved. 23 * Use is subject to license terms. 24 */ 25 26 /* 27 * ZFS control directory (a.k.a. ".zfs") 28 * 29 * This directory provides a common location for all ZFS meta-objects. 30 * Currently, this is only the 'snapshot' directory, but this may expand in the 31 * future. The elements are built using the GFS primitives, as the hierarchy 32 * does not actually exist on disk. 33 * 34 * For 'snapshot', we don't want to have all snapshots always mounted, because 35 * this would take up a huge amount of space in /etc/mnttab. We have three 36 * types of objects: 37 * 38 * ctldir ------> snapshotdir -------> snapshot 39 * | 40 * | 41 * V 42 * mounted fs 43 * 44 * The 'snapshot' node contains just enough information to lookup '..' and act 45 * as a mountpoint for the snapshot. Whenever we lookup a specific snapshot, we 46 * perform an automount of the underlying filesystem and return the 47 * corresponding vnode. 48 * 49 * All mounts are handled automatically by the kernel, but unmounts are 50 * (currently) handled from user land. The main reason is that there is no 51 * reliable way to auto-unmount the filesystem when it's "no longer in use". 52 * When the user unmounts a filesystem, we call zfsctl_unmount(), which 53 * unmounts any snapshots within the snapshot directory. 54 * 55 * The '.zfs', '.zfs/snapshot', and all directories created under 56 * '.zfs/snapshot' (ie: '.zfs/snapshot/<snapname>') are all GFS nodes and 57 * share the same vfs_t as the head filesystem (what '.zfs' lives under). 58 * 59 * File systems mounted ontop of the GFS nodes '.zfs/snapshot/<snapname>' 60 * (ie: snapshots) are ZFS nodes and have their own unique vfs_t. 61 * However, vnodes within these mounted on file systems have their v_vfsp 62 * fields set to the head filesystem to make NFS happy (see 63 * zfsctl_snapdir_lookup()). We VFS_HOLD the head filesystem's vfs_t 64 * so that it cannot be freed until all snapshots have been unmounted. 65 */ 66 67 #include <fs/fs_subr.h> 68 #include <sys/zfs_ctldir.h> 69 #include <sys/zfs_ioctl.h> 70 #include <sys/zfs_vfsops.h> 71 #include <sys/vfs_opreg.h> 72 #include <sys/gfs.h> 73 #include <sys/stat.h> 74 #include <sys/dmu.h> 75 #include <sys/dsl_deleg.h> 76 #include <sys/mount.h> 77 #include <sys/sunddi.h> 78 79 #include "zfs_namecheck.h" 80 81 typedef struct zfsctl_node { 82 gfs_dir_t zc_gfs_private; 83 uint64_t zc_id; 84 timestruc_t zc_cmtime; /* ctime and mtime, always the same */ 85 } zfsctl_node_t; 86 87 typedef struct zfsctl_snapdir { 88 zfsctl_node_t sd_node; 89 kmutex_t sd_lock; 90 avl_tree_t sd_snaps; 91 } zfsctl_snapdir_t; 92 93 typedef struct { 94 char *se_name; 95 vnode_t *se_root; 96 avl_node_t se_node; 97 } zfs_snapentry_t; 98 99 static int 100 snapentry_compare(const void *a, const void *b) 101 { 102 const zfs_snapentry_t *sa = a; 103 const zfs_snapentry_t *sb = b; 104 int ret = strcmp(sa->se_name, sb->se_name); 105 106 if (ret < 0) 107 return (-1); 108 else if (ret > 0) 109 return (1); 110 else 111 return (0); 112 } 113 114 //vnodeops_t *zfsctl_ops_shares_dir; 115 116 static struct vnodeopv_entry_desc zfsctl_ops_root; 117 static struct vnodeopv_entry_desc zfsctl_ops_snapdir; 118 static struct vnodeopv_entry_desc zfsctl_ops_snapshot; 119 static struct vnodeopv_entry_desc zfsctl_ops_shares; 120 121 122 static vnode_t *zfsctl_mknode_snapdir(vnode_t *); 123 static vnode_t *zfsctl_mknode_shares(vnode_t *); 124 static vnode_t *zfsctl_snapshot_mknode(vnode_t *, uint64_t objset); 125 static int zfsctl_unmount_snap(zfs_snapentry_t *, int, cred_t *); 126 127 static gfs_opsvec_t zfsctl_opsvec[] = { 128 { ".zfs", zfsctl_tops_root, &zfsctl_ops_root }, 129 { ".zfs/snapshot", zfsctl_tops_snapdir, &zfsctl_ops_snapdir }, 130 { ".zfs/snapshot/vnode", zfsctl_tops_snapshot, &zfsctl_ops_snapshot }, 131 { ".zfs/shares", zfsctl_tops_shares, &zfsctl_ops_shares_dir }, 132 { ".zfs/shares/vnode", zfsctl_tops_shares, &zfsctl_ops_shares }, 133 { NULL } 134 }; 135 136 /* 137 * Root directory elements. We only have two entries 138 * snapshot and shares. 139 */ 140 static gfs_dirent_t zfsctl_root_entries[] = { 141 { "snapshot", zfsctl_mknode_snapdir, GFS_CACHE_VNODE }, 142 { "shares", zfsctl_mknode_shares, GFS_CACHE_VNODE }, 143 { NULL } 144 }; 145 146 /* include . and .. in the calculation */ 147 #define NROOT_ENTRIES ((sizeof (zfsctl_root_entries) / \ 148 sizeof (gfs_dirent_t)) + 1) 149 150 151 /* 152 * Initialize the various GFS pieces we'll need to create and manipulate .zfs 153 * directories. This is called from the ZFS init routine, and initializes the 154 * vnode ops vectors that we'll be using. 155 */ 156 void 157 zfsctl_init(void) 158 { 159 } 160 161 void 162 zfsctl_fini(void) 163 { 164 } 165 166 /* 167 * Return the inode number associated with the 'snapshot' or 168 * 'shares' directory. 169 */ 170 /* ARGSUSED */ 171 static ino64_t 172 zfsctl_root_inode_cb(vnode_t *vp, int index) 173 { 174 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 175 176 ASSERT(index <= 2); 177 178 if (index == 0) 179 return (ZFSCTL_INO_SNAPDIR); 180 181 return (zfsvfs->z_shares_dir); 182 } 183 184 /* 185 * Create the '.zfs' directory. This directory is cached as part of the VFS 186 * structure. This results in a hold on the vfs_t. The code in zfs_umount() 187 * therefore checks against a vfs_count of 2 instead of 1. This reference 188 * is removed when the ctldir is destroyed in the unmount. 189 */ 190 void 191 zfsctl_create(zfsvfs_t *zfsvfs) 192 { 193 vnode_t *vp, *rvp; 194 zfsctl_node_t *zcp; 195 196 ASSERT(zfsvfs->z_ctldir == NULL); 197 198 vp = gfs_root_create(sizeof (zfsctl_node_t), zfsvfs->z_vfs, 199 zfsctl_ops_root, ZFSCTL_INO_ROOT, zfsctl_root_entries, 200 zfsctl_root_inode_cb, MAXNAMELEN, NULL, NULL); 201 zcp = vp->v_data; 202 zcp->zc_id = ZFSCTL_INO_ROOT; 203 204 VERIFY(VFS_ROOT(zfsvfs->z_vfs, &rvp) == 0); 205 ZFS_TIME_DECODE(&zcp->zc_cmtime, VTOZ(rvp)->z_phys->zp_crtime); 206 VN_RELE(rvp); 207 208 /* 209 * We're only faking the fact that we have a root of a filesystem for 210 * the sake of the GFS interfaces. Undo the flag manipulation it did 211 * for us. 212 */ 213 vp->v_flag &= ~(VROOT | VNOCACHE | VNOMAP | VNOSWAP | VNOMOUNT); 214 215 zfsvfs->z_ctldir = vp; 216 } 217 218 /* 219 * Destroy the '.zfs' directory. Only called when the filesystem is unmounted. 220 * There might still be more references if we were force unmounted, but only 221 * new zfs_inactive() calls can occur and they don't reference .zfs 222 */ 223 void 224 zfsctl_destroy(zfsvfs_t *zfsvfs) 225 { 226 VN_RELE(zfsvfs->z_ctldir); 227 zfsvfs->z_ctldir = NULL; 228 } 229 230 /* 231 * Given a root znode, retrieve the associated .zfs directory. 232 * Add a hold to the vnode and return it. 233 */ 234 vnode_t * 235 zfsctl_root(znode_t *zp) 236 { 237 ASSERT(zfs_has_ctldir(zp)); 238 VN_HOLD(zp->z_zfsvfs->z_ctldir); 239 return (zp->z_zfsvfs->z_ctldir); 240 } 241 242 /* 243 * Common open routine. Disallow any write access. 244 */ 245 /* ARGSUSED */ 246 static int 247 zfsctl_common_open(vnode_t **vpp, int flags, cred_t *cr, caller_context_t *ct) 248 { 249 if (flags & FWRITE) 250 return (EACCES); 251 252 return (0); 253 } 254 255 /* 256 * Common close routine. Nothing to do here. 257 */ 258 /* ARGSUSED */ 259 static int 260 zfsctl_common_close(vnode_t *vpp, int flags, int count, offset_t off, 261 cred_t *cr, caller_context_t *ct) 262 { 263 return (0); 264 } 265 266 /* 267 * Common access routine. Disallow writes. 268 */ 269 /* ARGSUSED */ 270 static int 271 zfsctl_common_access(vnode_t *vp, int mode, int flags, cred_t *cr, 272 caller_context_t *ct) 273 { 274 if (flags & V_ACE_MASK) { 275 if (mode & ACE_ALL_WRITE_PERMS) 276 return (EACCES); 277 } else { 278 if (mode & VWRITE) 279 return (EACCES); 280 } 281 282 return (0); 283 } 284 285 /* 286 * Common getattr function. Fill in basic information. 287 */ 288 static void 289 zfsctl_common_getattr(vnode_t *vp, vattr_t *vap) 290 { 291 timestruc_t now; 292 293 vap->va_uid = 0; 294 vap->va_gid = 0; 295 vap->va_rdev = 0; 296 /* 297 * We are a purely virtual object, so we have no 298 * blocksize or allocated blocks. 299 */ 300 vap->va_blksize = 0; 301 vap->va_nblocks = 0; 302 vap->va_seq = 0; 303 vap->va_fsid = vp->v_vfsp->vfs_dev; 304 vap->va_mode = S_IRUSR | S_IXUSR | S_IRGRP | S_IXGRP | 305 S_IROTH | S_IXOTH; 306 vap->va_type = VDIR; 307 /* 308 * We live in the now (for atime). 309 */ 310 gethrestime(&now); 311 vap->va_atime = now; 312 } 313 314 /*ARGSUSED*/ 315 static int 316 zfsctl_common_fid(vnode_t *vp, fid_t *fidp, caller_context_t *ct) 317 { 318 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 319 zfsctl_node_t *zcp = vp->v_data; 320 uint64_t object = zcp->zc_id; 321 zfid_short_t *zfid; 322 int i; 323 324 ZFS_ENTER(zfsvfs); 325 326 if (fidp->fid_len < SHORT_FID_LEN) { 327 fidp->fid_len = SHORT_FID_LEN; 328 ZFS_EXIT(zfsvfs); 329 return (ENOSPC); 330 } 331 332 zfid = (zfid_short_t *)fidp; 333 334 zfid->zf_len = SHORT_FID_LEN; 335 336 for (i = 0; i < sizeof (zfid->zf_object); i++) 337 zfid->zf_object[i] = (uint8_t)(object >> (8 * i)); 338 339 /* .zfs znodes always have a generation number of 0 */ 340 for (i = 0; i < sizeof (zfid->zf_gen); i++) 341 zfid->zf_gen[i] = 0; 342 343 ZFS_EXIT(zfsvfs); 344 return (0); 345 } 346 347 348 /*ARGSUSED*/ 349 static int 350 zfsctl_shares_fid(vnode_t *vp, fid_t *fidp, caller_context_t *ct) 351 { 352 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 353 znode_t *dzp; 354 int error; 355 356 ZFS_ENTER(zfsvfs); 357 358 if (zfsvfs->z_shares_dir == 0) { 359 ZFS_EXIT(zfsvfs); 360 return (ENOTSUP); 361 } 362 363 if ((error = zfs_zget(zfsvfs, zfsvfs->z_shares_dir, &dzp)) == 0) { 364 error = VOP_FID(ZTOV(dzp), fidp, ct); 365 VN_RELE(ZTOV(dzp)); 366 } 367 368 ZFS_EXIT(zfsvfs); 369 return (error); 370 } 371 /* 372 * .zfs inode namespace 373 * 374 * We need to generate unique inode numbers for all files and directories 375 * within the .zfs pseudo-filesystem. We use the following scheme: 376 * 377 * ENTRY ZFSCTL_INODE 378 * .zfs 1 379 * .zfs/snapshot 2 380 * .zfs/snapshot/<snap> objectid(snap) 381 */ 382 383 #define ZFSCTL_INO_SNAP(id) (id) 384 385 /* 386 * Get root directory attributes. 387 */ 388 /* ARGSUSED */ 389 static int 390 zfsctl_root_getattr(vnode_t *vp, vattr_t *vap, int flags, cred_t *cr, 391 caller_context_t *ct) 392 { 393 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 394 zfsctl_node_t *zcp = vp->v_data; 395 396 ZFS_ENTER(zfsvfs); 397 vap->va_nodeid = ZFSCTL_INO_ROOT; 398 vap->va_nlink = vap->va_size = NROOT_ENTRIES; 399 vap->va_mtime = vap->va_ctime = zcp->zc_cmtime; 400 401 zfsctl_common_getattr(vp, vap); 402 ZFS_EXIT(zfsvfs); 403 404 return (0); 405 } 406 407 /* 408 * Special case the handling of "..". 409 */ 410 /* ARGSUSED */ 411 int 412 zfsctl_root_lookup(vnode_t *dvp, char *nm, vnode_t **vpp, pathname_t *pnp, 413 int flags, vnode_t *rdir, cred_t *cr, caller_context_t *ct, 414 int *direntflags, pathname_t *realpnp) 415 { 416 zfsvfs_t *zfsvfs = dvp->v_vfsp->vfs_data; 417 int err; 418 419 /* 420 * No extended attributes allowed under .zfs 421 */ 422 if (flags & LOOKUP_XATTR) 423 return (EINVAL); 424 425 ZFS_ENTER(zfsvfs); 426 427 if (strcmp(nm, "..") == 0) { 428 err = VFS_ROOT(dvp->v_vfsp, vpp); 429 } else { 430 err = gfs_vop_lookup(dvp, nm, vpp, pnp, flags, rdir, 431 cr, ct, direntflags, realpnp); 432 } 433 434 ZFS_EXIT(zfsvfs); 435 436 return (err); 437 } 438 439 static int 440 zfsctl_pathconf(vnode_t *vp, int cmd, ulong_t *valp, cred_t *cr, 441 caller_context_t *ct) 442 { 443 /* 444 * We only care about ACL_ENABLED so that libsec can 445 * display ACL correctly and not default to POSIX draft. 446 */ 447 if (cmd == _PC_ACL_ENABLED) { 448 *valp = _ACL_ACE_ENABLED; 449 return (0); 450 } 451 452 return (fs_pathconf(vp, cmd, valp, cr, ct)); 453 } 454 455 static const fs_operation_def_t zfsctl_tops_root[] = { 456 { VOPNAME_OPEN, { .vop_open = zfsctl_common_open } }, 457 { VOPNAME_CLOSE, { .vop_close = zfsctl_common_close } }, 458 { VOPNAME_IOCTL, { .error = fs_inval } }, 459 { VOPNAME_GETATTR, { .vop_getattr = zfsctl_root_getattr } }, 460 { VOPNAME_ACCESS, { .vop_access = zfsctl_common_access } }, 461 { VOPNAME_READDIR, { .vop_readdir = gfs_vop_readdir } }, 462 { VOPNAME_LOOKUP, { .vop_lookup = zfsctl_root_lookup } }, 463 { VOPNAME_SEEK, { .vop_seek = fs_seek } }, 464 { VOPNAME_INACTIVE, { .vop_inactive = gfs_vop_inactive } }, 465 { VOPNAME_PATHCONF, { .vop_pathconf = zfsctl_pathconf } }, 466 { VOPNAME_FID, { .vop_fid = zfsctl_common_fid } }, 467 { NULL } 468 }; 469 470 static int 471 zfsctl_snapshot_zname(vnode_t *vp, const char *name, int len, char *zname) 472 { 473 objset_t *os = ((zfsvfs_t *)((vp)->v_vfsp->vfs_data))->z_os; 474 475 if (snapshot_namecheck(name, NULL, NULL) != 0) 476 return (EILSEQ); 477 dmu_objset_name(os, zname); 478 if (strlen(zname) + 1 + strlen(name) >= len) 479 return (ENAMETOOLONG); 480 (void) strcat(zname, "@"); 481 (void) strcat(zname, name); 482 return (0); 483 } 484 485 static int 486 zfsctl_unmount_snap(zfs_snapentry_t *sep, int fflags, cred_t *cr) 487 { 488 vnode_t *svp = sep->se_root; 489 int error; 490 491 ASSERT(vn_ismntpt(svp)); 492 493 /* this will be dropped by dounmount() */ 494 if ((error = vn_vfswlock(svp)) != 0) 495 return (error); 496 497 VN_HOLD(svp); 498 error = dounmount(vn_mountedvfs(svp), fflags, cr); 499 if (error) { 500 VN_RELE(svp); 501 return (error); 502 } 503 504 /* 505 * We can't use VN_RELE(), as that will try to invoke 506 * zfsctl_snapdir_inactive(), which would cause us to destroy 507 * the sd_lock mutex held by our caller. 508 */ 509 ASSERT(svp->v_count == 1); 510 gfs_vop_inactive(svp, cr, NULL); 511 512 kmem_free(sep->se_name, strlen(sep->se_name) + 1); 513 kmem_free(sep, sizeof (zfs_snapentry_t)); 514 515 return (0); 516 } 517 518 static void 519 zfsctl_rename_snap(zfsctl_snapdir_t *sdp, zfs_snapentry_t *sep, const char *nm) 520 { 521 avl_index_t where; 522 vfs_t *vfsp; 523 refstr_t *pathref; 524 char newpath[MAXNAMELEN]; 525 char *tail; 526 527 ASSERT(MUTEX_HELD(&sdp->sd_lock)); 528 ASSERT(sep != NULL); 529 530 vfsp = vn_mountedvfs(sep->se_root); 531 ASSERT(vfsp != NULL); 532 533 vfs_lock_wait(vfsp); 534 535 /* 536 * Change the name in the AVL tree. 537 */ 538 avl_remove(&sdp->sd_snaps, sep); 539 kmem_free(sep->se_name, strlen(sep->se_name) + 1); 540 sep->se_name = kmem_alloc(strlen(nm) + 1, KM_SLEEP); 541 (void) strcpy(sep->se_name, nm); 542 VERIFY(avl_find(&sdp->sd_snaps, sep, &where) == NULL); 543 avl_insert(&sdp->sd_snaps, sep, where); 544 545 /* 546 * Change the current mountpoint info: 547 * - update the tail of the mntpoint path 548 * - update the tail of the resource path 549 */ 550 pathref = vfs_getmntpoint(vfsp); 551 (void) strncpy(newpath, refstr_value(pathref), sizeof (newpath)); 552 VERIFY((tail = strrchr(newpath, '/')) != NULL); 553 *(tail+1) = '\0'; 554 ASSERT3U(strlen(newpath) + strlen(nm), <, sizeof (newpath)); 555 (void) strcat(newpath, nm); 556 refstr_rele(pathref); 557 vfs_setmntpoint(vfsp, newpath); 558 559 pathref = vfs_getresource(vfsp); 560 (void) strncpy(newpath, refstr_value(pathref), sizeof (newpath)); 561 VERIFY((tail = strrchr(newpath, '@')) != NULL); 562 *(tail+1) = '\0'; 563 ASSERT3U(strlen(newpath) + strlen(nm), <, sizeof (newpath)); 564 (void) strcat(newpath, nm); 565 refstr_rele(pathref); 566 vfs_setresource(vfsp, newpath); 567 568 vfs_unlock(vfsp); 569 } 570 571 /*ARGSUSED*/ 572 static int 573 zfsctl_snapdir_rename(vnode_t *sdvp, char *snm, vnode_t *tdvp, char *tnm, 574 cred_t *cr, caller_context_t *ct, int flags) 575 { 576 zfsctl_snapdir_t *sdp = sdvp->v_data; 577 zfs_snapentry_t search, *sep; 578 zfsvfs_t *zfsvfs; 579 avl_index_t where; 580 char from[MAXNAMELEN], to[MAXNAMELEN]; 581 char real[MAXNAMELEN]; 582 int err; 583 584 zfsvfs = sdvp->v_vfsp->vfs_data; 585 ZFS_ENTER(zfsvfs); 586 587 if ((flags & FIGNORECASE) || zfsvfs->z_case == ZFS_CASE_INSENSITIVE) { 588 err = dmu_snapshot_realname(zfsvfs->z_os, snm, real, 589 MAXNAMELEN, NULL); 590 if (err == 0) { 591 snm = real; 592 } else if (err != ENOTSUP) { 593 ZFS_EXIT(zfsvfs); 594 return (err); 595 } 596 } 597 598 ZFS_EXIT(zfsvfs); 599 600 err = zfsctl_snapshot_zname(sdvp, snm, MAXNAMELEN, from); 601 if (!err) 602 err = zfsctl_snapshot_zname(tdvp, tnm, MAXNAMELEN, to); 603 if (!err) 604 err = zfs_secpolicy_rename_perms(from, to, cr); 605 if (err) 606 return (err); 607 608 /* 609 * Cannot move snapshots out of the snapdir. 610 */ 611 if (sdvp != tdvp) 612 return (EINVAL); 613 614 if (strcmp(snm, tnm) == 0) 615 return (0); 616 617 mutex_enter(&sdp->sd_lock); 618 619 search.se_name = (char *)snm; 620 if ((sep = avl_find(&sdp->sd_snaps, &search, &where)) == NULL) { 621 mutex_exit(&sdp->sd_lock); 622 return (ENOENT); 623 } 624 625 err = dmu_objset_rename(from, to, B_FALSE); 626 if (err == 0) 627 zfsctl_rename_snap(sdp, sep, tnm); 628 629 mutex_exit(&sdp->sd_lock); 630 631 return (err); 632 } 633 634 /* ARGSUSED */ 635 static int 636 zfsctl_snapdir_remove(vnode_t *dvp, char *name, vnode_t *cwd, cred_t *cr, 637 caller_context_t *ct, int flags) 638 { 639 zfsctl_snapdir_t *sdp = dvp->v_data; 640 zfs_snapentry_t *sep; 641 zfs_snapentry_t search; 642 zfsvfs_t *zfsvfs; 643 char snapname[MAXNAMELEN]; 644 char real[MAXNAMELEN]; 645 int err; 646 647 zfsvfs = dvp->v_vfsp->vfs_data; 648 ZFS_ENTER(zfsvfs); 649 650 if ((flags & FIGNORECASE) || zfsvfs->z_case == ZFS_CASE_INSENSITIVE) { 651 652 err = dmu_snapshot_realname(zfsvfs->z_os, name, real, 653 MAXNAMELEN, NULL); 654 if (err == 0) { 655 name = real; 656 } else if (err != ENOTSUP) { 657 ZFS_EXIT(zfsvfs); 658 return (err); 659 } 660 } 661 662 ZFS_EXIT(zfsvfs); 663 664 err = zfsctl_snapshot_zname(dvp, name, MAXNAMELEN, snapname); 665 if (!err) 666 err = zfs_secpolicy_destroy_perms(snapname, cr); 667 if (err) 668 return (err); 669 670 mutex_enter(&sdp->sd_lock); 671 672 search.se_name = name; 673 sep = avl_find(&sdp->sd_snaps, &search, NULL); 674 if (sep) { 675 avl_remove(&sdp->sd_snaps, sep); 676 err = zfsctl_unmount_snap(sep, MS_FORCE, cr); 677 if (err) 678 avl_add(&sdp->sd_snaps, sep); 679 else 680 err = dmu_objset_destroy(snapname, B_FALSE); 681 } else { 682 err = ENOENT; 683 } 684 685 mutex_exit(&sdp->sd_lock); 686 687 return (err); 688 } 689 690 /* 691 * This creates a snapshot under '.zfs/snapshot'. 692 */ 693 /* ARGSUSED */ 694 static int 695 zfsctl_snapdir_mkdir(vnode_t *dvp, char *dirname, vattr_t *vap, vnode_t **vpp, 696 cred_t *cr, caller_context_t *cc, int flags, vsecattr_t *vsecp) 697 { 698 zfsvfs_t *zfsvfs = dvp->v_vfsp->vfs_data; 699 char name[MAXNAMELEN]; 700 int err; 701 static enum symfollow follow = NO_FOLLOW; 702 static enum uio_seg seg = UIO_SYSSPACE; 703 704 if (snapshot_namecheck(dirname, NULL, NULL) != 0) 705 return (EILSEQ); 706 707 dmu_objset_name(zfsvfs->z_os, name); 708 709 *vpp = NULL; 710 711 err = zfs_secpolicy_snapshot_perms(name, cr); 712 if (err) 713 return (err); 714 715 if (err == 0) { 716 err = dmu_objset_snapshot(name, dirname, NULL, B_FALSE); 717 if (err) 718 return (err); 719 err = lookupnameat(dirname, seg, follow, NULL, vpp, dvp); 720 } 721 722 return (err); 723 } 724 725 /* 726 * Lookup entry point for the 'snapshot' directory. Try to open the 727 * snapshot if it exist, creating the pseudo filesystem vnode as necessary. 728 * Perform a mount of the associated dataset on top of the vnode. 729 */ 730 /* ARGSUSED */ 731 static int 732 zfsctl_snapdir_lookup(vnode_t *dvp, char *nm, vnode_t **vpp, pathname_t *pnp, 733 int flags, vnode_t *rdir, cred_t *cr, caller_context_t *ct, 734 int *direntflags, pathname_t *realpnp) 735 { 736 zfsctl_snapdir_t *sdp = dvp->v_data; 737 objset_t *snap; 738 char snapname[MAXNAMELEN]; 739 char real[MAXNAMELEN]; 740 char *mountpoint; 741 zfs_snapentry_t *sep, search; 742 struct mounta margs; 743 vfs_t *vfsp; 744 size_t mountpoint_len; 745 avl_index_t where; 746 zfsvfs_t *zfsvfs = dvp->v_vfsp->vfs_data; 747 int err; 748 749 /* 750 * No extended attributes allowed under .zfs 751 */ 752 if (flags & LOOKUP_XATTR) 753 return (EINVAL); 754 755 ASSERT(dvp->v_type == VDIR); 756 757 /* 758 * If we get a recursive call, that means we got called 759 * from the domount() code while it was trying to look up the 760 * spec (which looks like a local path for zfs). We need to 761 * add some flag to domount() to tell it not to do this lookup. 762 */ 763 if (MUTEX_HELD(&sdp->sd_lock)) 764 return (ENOENT); 765 766 ZFS_ENTER(zfsvfs); 767 768 if (gfs_lookup_dot(vpp, dvp, zfsvfs->z_ctldir, nm) == 0) { 769 ZFS_EXIT(zfsvfs); 770 return (0); 771 } 772 773 if (flags & FIGNORECASE) { 774 boolean_t conflict = B_FALSE; 775 776 err = dmu_snapshot_realname(zfsvfs->z_os, nm, real, 777 MAXNAMELEN, &conflict); 778 if (err == 0) { 779 nm = real; 780 } else if (err != ENOTSUP) { 781 ZFS_EXIT(zfsvfs); 782 return (err); 783 } 784 if (realpnp) 785 (void) strlcpy(realpnp->pn_buf, nm, 786 realpnp->pn_bufsize); 787 if (conflict && direntflags) 788 *direntflags = ED_CASE_CONFLICT; 789 } 790 791 mutex_enter(&sdp->sd_lock); 792 search.se_name = (char *)nm; 793 if ((sep = avl_find(&sdp->sd_snaps, &search, &where)) != NULL) { 794 *vpp = sep->se_root; 795 VN_HOLD(*vpp); 796 err = traverse(vpp); 797 if (err) { 798 VN_RELE(*vpp); 799 *vpp = NULL; 800 } else if (*vpp == sep->se_root) { 801 /* 802 * The snapshot was unmounted behind our backs, 803 * try to remount it. 804 */ 805 goto domount; 806 } else { 807 /* 808 * VROOT was set during the traverse call. We need 809 * to clear it since we're pretending to be part 810 * of our parent's vfs. 811 */ 812 (*vpp)->v_flag &= ~VROOT; 813 } 814 mutex_exit(&sdp->sd_lock); 815 ZFS_EXIT(zfsvfs); 816 return (err); 817 } 818 819 /* 820 * The requested snapshot is not currently mounted, look it up. 821 */ 822 err = zfsctl_snapshot_zname(dvp, nm, MAXNAMELEN, snapname); 823 if (err) { 824 mutex_exit(&sdp->sd_lock); 825 ZFS_EXIT(zfsvfs); 826 /* 827 * handle "ls *" or "?" in a graceful manner, 828 * forcing EILSEQ to ENOENT. 829 * Since shell ultimately passes "*" or "?" as name to lookup 830 */ 831 return (err == EILSEQ ? ENOENT : err); 832 } 833 if (dmu_objset_hold(snapname, FTAG, &snap) != 0) { 834 mutex_exit(&sdp->sd_lock); 835 ZFS_EXIT(zfsvfs); 836 return (ENOENT); 837 } 838 839 sep = kmem_alloc(sizeof (zfs_snapentry_t), KM_SLEEP); 840 sep->se_name = kmem_alloc(strlen(nm) + 1, KM_SLEEP); 841 (void) strcpy(sep->se_name, nm); 842 *vpp = sep->se_root = zfsctl_snapshot_mknode(dvp, dmu_objset_id(snap)); 843 avl_insert(&sdp->sd_snaps, sep, where); 844 845 dmu_objset_rele(snap, FTAG); 846 domount: 847 mountpoint_len = strlen(refstr_value(dvp->v_vfsp->vfs_mntpt)) + 848 strlen("/.zfs/snapshot/") + strlen(nm) + 1; 849 mountpoint = kmem_alloc(mountpoint_len, KM_SLEEP); 850 (void) snprintf(mountpoint, mountpoint_len, "%s/.zfs/snapshot/%s", 851 refstr_value(dvp->v_vfsp->vfs_mntpt), nm); 852 853 margs.spec = snapname; 854 margs.dir = mountpoint; 855 margs.flags = MS_SYSSPACE | MS_NOMNTTAB; 856 margs.fstype = "zfs"; 857 margs.dataptr = NULL; 858 margs.datalen = 0; 859 margs.optptr = NULL; 860 margs.optlen = 0; 861 862 err = domount("zfs", &margs, *vpp, kcred, &vfsp); 863 kmem_free(mountpoint, mountpoint_len); 864 865 if (err == 0) { 866 /* 867 * Return the mounted root rather than the covered mount point. 868 * Takes the GFS vnode at .zfs/snapshot/<snapname> and returns 869 * the ZFS vnode mounted on top of the GFS node. This ZFS 870 * vnode is the root of the newly created vfsp. 871 */ 872 VFS_RELE(vfsp); 873 err = traverse(vpp); 874 } 875 876 if (err == 0) { 877 /* 878 * Fix up the root vnode mounted on .zfs/snapshot/<snapname>. 879 * 880 * This is where we lie about our v_vfsp in order to 881 * make .zfs/snapshot/<snapname> accessible over NFS 882 * without requiring manual mounts of <snapname>. 883 */ 884 ASSERT(VTOZ(*vpp)->z_zfsvfs != zfsvfs); 885 VTOZ(*vpp)->z_zfsvfs->z_parent = zfsvfs; 886 (*vpp)->v_vfsp = zfsvfs->z_vfs; 887 (*vpp)->v_flag &= ~VROOT; 888 } 889 mutex_exit(&sdp->sd_lock); 890 ZFS_EXIT(zfsvfs); 891 892 /* 893 * If we had an error, drop our hold on the vnode and 894 * zfsctl_snapshot_inactive() will clean up. 895 */ 896 if (err) { 897 VN_RELE(*vpp); 898 *vpp = NULL; 899 } 900 return (err); 901 } 902 903 /* ARGSUSED */ 904 static int 905 zfsctl_shares_lookup(vnode_t *dvp, char *nm, vnode_t **vpp, pathname_t *pnp, 906 int flags, vnode_t *rdir, cred_t *cr, caller_context_t *ct, 907 int *direntflags, pathname_t *realpnp) 908 { 909 zfsvfs_t *zfsvfs = dvp->v_vfsp->vfs_data; 910 znode_t *dzp; 911 int error; 912 913 ZFS_ENTER(zfsvfs); 914 915 if (gfs_lookup_dot(vpp, dvp, zfsvfs->z_ctldir, nm) == 0) { 916 ZFS_EXIT(zfsvfs); 917 return (0); 918 } 919 920 if (zfsvfs->z_shares_dir == 0) { 921 ZFS_EXIT(zfsvfs); 922 return (ENOTSUP); 923 } 924 if ((error = zfs_zget(zfsvfs, zfsvfs->z_shares_dir, &dzp)) == 0) 925 error = VOP_LOOKUP(ZTOV(dzp), nm, vpp, pnp, 926 flags, rdir, cr, ct, direntflags, realpnp); 927 928 VN_RELE(ZTOV(dzp)); 929 ZFS_EXIT(zfsvfs); 930 931 return (error); 932 } 933 934 /* ARGSUSED */ 935 static int 936 zfsctl_snapdir_readdir_cb(vnode_t *vp, void *dp, int *eofp, 937 offset_t *offp, offset_t *nextp, void *data, int flags) 938 { 939 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 940 char snapname[MAXNAMELEN]; 941 uint64_t id, cookie; 942 boolean_t case_conflict; 943 int error; 944 945 ZFS_ENTER(zfsvfs); 946 947 cookie = *offp; 948 error = dmu_snapshot_list_next(zfsvfs->z_os, MAXNAMELEN, snapname, &id, 949 &cookie, &case_conflict); 950 if (error) { 951 ZFS_EXIT(zfsvfs); 952 if (error == ENOENT) { 953 *eofp = 1; 954 return (0); 955 } 956 return (error); 957 } 958 959 if (flags & V_RDDIR_ENTFLAGS) { 960 edirent_t *eodp = dp; 961 962 (void) strcpy(eodp->ed_name, snapname); 963 eodp->ed_ino = ZFSCTL_INO_SNAP(id); 964 eodp->ed_eflags = case_conflict ? ED_CASE_CONFLICT : 0; 965 } else { 966 struct dirent64 *odp = dp; 967 968 (void) strcpy(odp->d_name, snapname); 969 odp->d_ino = ZFSCTL_INO_SNAP(id); 970 } 971 *nextp = cookie; 972 973 ZFS_EXIT(zfsvfs); 974 975 return (0); 976 } 977 978 /* ARGSUSED */ 979 static int 980 zfsctl_shares_readdir(vnode_t *vp, uio_t *uiop, cred_t *cr, int *eofp, 981 caller_context_t *ct, int flags) 982 { 983 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 984 znode_t *dzp; 985 int error; 986 987 ZFS_ENTER(zfsvfs); 988 989 if (zfsvfs->z_shares_dir == 0) { 990 ZFS_EXIT(zfsvfs); 991 return (ENOTSUP); 992 } 993 if ((error = zfs_zget(zfsvfs, zfsvfs->z_shares_dir, &dzp)) == 0) { 994 error = VOP_READDIR(ZTOV(dzp), uiop, cr, eofp, ct, flags); 995 VN_RELE(ZTOV(dzp)); 996 } else { 997 *eofp = 1; 998 error = ENOENT; 999 } 1000 1001 ZFS_EXIT(zfsvfs); 1002 return (error); 1003 } 1004 1005 /* 1006 * pvp is the '.zfs' directory (zfsctl_node_t). 1007 * Creates vp, which is '.zfs/snapshot' (zfsctl_snapdir_t). 1008 * 1009 * This function is the callback to create a GFS vnode for '.zfs/snapshot' 1010 * when a lookup is performed on .zfs for "snapshot". 1011 */ 1012 vnode_t * 1013 zfsctl_mknode_snapdir(vnode_t *pvp) 1014 { 1015 vnode_t *vp; 1016 zfsctl_snapdir_t *sdp; 1017 1018 vp = gfs_dir_create(sizeof (zfsctl_snapdir_t), pvp, 1019 zfsctl_ops_snapdir, NULL, NULL, MAXNAMELEN, 1020 zfsctl_snapdir_readdir_cb, NULL); 1021 sdp = vp->v_data; 1022 sdp->sd_node.zc_id = ZFSCTL_INO_SNAPDIR; 1023 sdp->sd_node.zc_cmtime = ((zfsctl_node_t *)pvp->v_data)->zc_cmtime; 1024 mutex_init(&sdp->sd_lock, NULL, MUTEX_DEFAULT, NULL); 1025 avl_create(&sdp->sd_snaps, snapentry_compare, 1026 sizeof (zfs_snapentry_t), offsetof(zfs_snapentry_t, se_node)); 1027 return (vp); 1028 } 1029 1030 vnode_t * 1031 zfsctl_mknode_shares(vnode_t *pvp) 1032 { 1033 vnode_t *vp; 1034 zfsctl_node_t *sdp; 1035 1036 vp = gfs_dir_create(sizeof (zfsctl_node_t), pvp, 1037 zfsctl_ops_shares, NULL, NULL, MAXNAMELEN, 1038 NULL, NULL); 1039 sdp = vp->v_data; 1040 sdp->zc_cmtime = ((zfsctl_node_t *)pvp->v_data)->zc_cmtime; 1041 return (vp); 1042 1043 } 1044 1045 /* ARGSUSED */ 1046 static int 1047 zfsctl_shares_getattr(vnode_t *vp, vattr_t *vap, int flags, cred_t *cr, 1048 caller_context_t *ct) 1049 { 1050 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 1051 znode_t *dzp; 1052 int error; 1053 1054 ZFS_ENTER(zfsvfs); 1055 if (zfsvfs->z_shares_dir == 0) { 1056 ZFS_EXIT(zfsvfs); 1057 return (ENOTSUP); 1058 } 1059 if ((error = zfs_zget(zfsvfs, zfsvfs->z_shares_dir, &dzp)) == 0) { 1060 error = VOP_GETATTR(ZTOV(dzp), vap, flags, cr, ct); 1061 VN_RELE(ZTOV(dzp)); 1062 } 1063 ZFS_EXIT(zfsvfs); 1064 return (error); 1065 1066 1067 } 1068 1069 /* ARGSUSED */ 1070 static int 1071 zfsctl_snapdir_getattr(vnode_t *vp, vattr_t *vap, int flags, cred_t *cr, 1072 caller_context_t *ct) 1073 { 1074 zfsvfs_t *zfsvfs = vp->v_vfsp->vfs_data; 1075 zfsctl_snapdir_t *sdp = vp->v_data; 1076 1077 ZFS_ENTER(zfsvfs); 1078 zfsctl_common_getattr(vp, vap); 1079 vap->va_nodeid = gfs_file_inode(vp); 1080 vap->va_nlink = vap->va_size = avl_numnodes(&sdp->sd_snaps) + 2; 1081 vap->va_ctime = vap->va_mtime = dmu_objset_snap_cmtime(zfsvfs->z_os); 1082 ZFS_EXIT(zfsvfs); 1083 1084 return (0); 1085 } 1086 1087 /* ARGSUSED */ 1088 static void 1089 zfsctl_snapdir_inactive(vnode_t *vp, cred_t *cr, caller_context_t *ct) 1090 { 1091 zfsctl_snapdir_t *sdp = vp->v_data; 1092 void *private; 1093 1094 private = gfs_dir_inactive(vp); 1095 if (private != NULL) { 1096 ASSERT(avl_numnodes(&sdp->sd_snaps) == 0); 1097 mutex_destroy(&sdp->sd_lock); 1098 avl_destroy(&sdp->sd_snaps); 1099 kmem_free(private, sizeof (zfsctl_snapdir_t)); 1100 } 1101 } 1102 1103 #ifndef __NetBSD__ 1104 static const fs_operation_def_t zfsctl_tops_snapdir[] = { 1105 { VOPNAME_OPEN, { .vop_open = zfsctl_common_open } }, 1106 { VOPNAME_CLOSE, { .vop_close = zfsctl_common_close } }, 1107 { VOPNAME_IOCTL, { .error = fs_inval } }, 1108 { VOPNAME_GETATTR, { .vop_getattr = zfsctl_snapdir_getattr } }, 1109 { VOPNAME_ACCESS, { .vop_access = zfsctl_common_access } }, 1110 { VOPNAME_RENAME, { .vop_rename = zfsctl_snapdir_rename } }, 1111 { VOPNAME_RMDIR, { .vop_rmdir = zfsctl_snapdir_remove } }, 1112 { VOPNAME_MKDIR, { .vop_mkdir = zfsctl_snapdir_mkdir } }, 1113 { VOPNAME_READDIR, { .vop_readdir = gfs_vop_readdir } }, 1114 { VOPNAME_LOOKUP, { .vop_lookup = zfsctl_snapdir_lookup } }, 1115 { VOPNAME_SEEK, { .vop_seek = fs_seek } }, 1116 { VOPNAME_INACTIVE, { .vop_inactive = zfsctl_snapdir_inactive } }, 1117 { VOPNAME_FID, { .vop_fid = zfsctl_common_fid } }, 1118 { NULL } 1119 }; 1120 1121 static const fs_operation_def_t zfsctl_tops_shares[] = { 1122 { VOPNAME_OPEN, { .vop_open = zfsctl_common_open } }, 1123 { VOPNAME_CLOSE, { .vop_close = zfsctl_common_close } }, 1124 { VOPNAME_IOCTL, { .error = fs_inval } }, 1125 { VOPNAME_GETATTR, { .vop_getattr = zfsctl_shares_getattr } }, 1126 { VOPNAME_ACCESS, { .vop_access = zfsctl_common_access } }, 1127 { VOPNAME_READDIR, { .vop_readdir = zfsctl_shares_readdir } }, 1128 { VOPNAME_LOOKUP, { .vop_lookup = zfsctl_shares_lookup } }, 1129 { VOPNAME_SEEK, { .vop_seek = fs_seek } }, 1130 { VOPNAME_INACTIVE, { .vop_inactive = gfs_vop_inactive } }, 1131 { VOPNAME_FID, { .vop_fid = zfsctl_shares_fid } }, 1132 { NULL } 1133 }; 1134 #endif 1135 /* 1136 * pvp is the GFS vnode '.zfs/snapshot'. 1137 * 1138 * This creates a GFS node under '.zfs/snapshot' representing each 1139 * snapshot. This newly created GFS node is what we mount snapshot 1140 * vfs_t's ontop of. 1141 */ 1142 static vnode_t * 1143 zfsctl_snapshot_mknode(vnode_t *pvp, uint64_t objset) 1144 { 1145 vnode_t *vp; 1146 zfsctl_node_t *zcp; 1147 1148 vp = gfs_dir_create(sizeof (zfsctl_node_t), pvp, 1149 zfsctl_ops_snapshot, NULL, NULL, MAXNAMELEN, NULL, NULL); 1150 zcp = vp->v_data; 1151 zcp->zc_id = objset; 1152 1153 return (vp); 1154 } 1155 1156 static void 1157 zfsctl_snapshot_inactive(vnode_t *vp, cred_t *cr, caller_context_t *ct) 1158 { 1159 zfsctl_snapdir_t *sdp; 1160 zfs_snapentry_t *sep, *next; 1161 vnode_t *dvp; 1162 1163 VERIFY(gfs_dir_lookup(vp, "..", &dvp, cr, 0, NULL, NULL) == 0); 1164 sdp = dvp->v_data; 1165 1166 mutex_enter(&sdp->sd_lock); 1167 1168 if (vp->v_count > 1) { 1169 mutex_exit(&sdp->sd_lock); 1170 return; 1171 } 1172 ASSERT(!vn_ismntpt(vp)); 1173 1174 sep = avl_first(&sdp->sd_snaps); 1175 while (sep != NULL) { 1176 next = AVL_NEXT(&sdp->sd_snaps, sep); 1177 1178 if (sep->se_root == vp) { 1179 avl_remove(&sdp->sd_snaps, sep); 1180 kmem_free(sep->se_name, strlen(sep->se_name) + 1); 1181 kmem_free(sep, sizeof (zfs_snapentry_t)); 1182 break; 1183 } 1184 sep = next; 1185 } 1186 ASSERT(sep != NULL); 1187 1188 mutex_exit(&sdp->sd_lock); 1189 VN_RELE(dvp); 1190 1191 /* 1192 * Dispose of the vnode for the snapshot mount point. 1193 * This is safe to do because once this entry has been removed 1194 * from the AVL tree, it can't be found again, so cannot become 1195 * "active". If we lookup the same name again we will end up 1196 * creating a new vnode. 1197 */ 1198 gfs_vop_inactive(vp, cr, ct); 1199 } 1200 1201 #ifndef __NetBSD__ 1202 /* 1203 * These VP's should never see the light of day. They should always 1204 * be covered. 1205 */ 1206 static const fs_operation_def_t zfsctl_tops_snapshot[] = { 1207 VOPNAME_INACTIVE, { .vop_inactive = zfsctl_snapshot_inactive }, 1208 NULL, NULL 1209 }; 1210 #endif 1211 1212 int 1213 zfsctl_lookup_objset(vfs_t *vfsp, uint64_t objsetid, zfsvfs_t **zfsvfsp) 1214 { 1215 zfsvfs_t *zfsvfs = vfsp->vfs_data; 1216 vnode_t *dvp, *vp; 1217 zfsctl_snapdir_t *sdp; 1218 zfsctl_node_t *zcp; 1219 zfs_snapentry_t *sep; 1220 int error; 1221 1222 ASSERT(zfsvfs->z_ctldir != NULL); 1223 error = zfsctl_root_lookup(zfsvfs->z_ctldir, "snapshot", &dvp, 1224 NULL, 0, NULL, kcred, NULL, NULL, NULL); 1225 if (error != 0) 1226 return (error); 1227 sdp = dvp->v_data; 1228 1229 mutex_enter(&sdp->sd_lock); 1230 sep = avl_first(&sdp->sd_snaps); 1231 while (sep != NULL) { 1232 vp = sep->se_root; 1233 zcp = vp->v_data; 1234 if (zcp->zc_id == objsetid) 1235 break; 1236 1237 sep = AVL_NEXT(&sdp->sd_snaps, sep); 1238 } 1239 1240 if (sep != NULL) { 1241 VN_HOLD(vp); 1242 /* 1243 * Return the mounted root rather than the covered mount point. 1244 * Takes the GFS vnode at .zfs/snapshot/<snapshot objsetid> 1245 * and returns the ZFS vnode mounted on top of the GFS node. 1246 * This ZFS vnode is the root of the vfs for objset 'objsetid'. 1247 */ 1248 error = traverse(&vp); 1249 if (error == 0) { 1250 if (vp == sep->se_root) 1251 error = EINVAL; 1252 else 1253 *zfsvfsp = VTOZ(vp)->z_zfsvfs; 1254 } 1255 mutex_exit(&sdp->sd_lock); 1256 VN_RELE(vp); 1257 } else { 1258 error = EINVAL; 1259 mutex_exit(&sdp->sd_lock); 1260 } 1261 1262 VN_RELE(dvp); 1263 1264 return (error); 1265 } 1266 1267 /* 1268 * Unmount any snapshots for the given filesystem. This is called from 1269 * zfs_umount() - if we have a ctldir, then go through and unmount all the 1270 * snapshots. 1271 */ 1272 int 1273 zfsctl_umount_snapshots(vfs_t *vfsp, int fflags, cred_t *cr) 1274 { 1275 zfsvfs_t *zfsvfs = vfsp->vfs_data; 1276 vnode_t *dvp; 1277 zfsctl_snapdir_t *sdp; 1278 zfs_snapentry_t *sep, *next; 1279 int error; 1280 1281 ASSERT(zfsvfs->z_ctldir != NULL); 1282 error = zfsctl_root_lookup(zfsvfs->z_ctldir, "snapshot", &dvp, 1283 NULL, 0, NULL, cr, NULL, NULL, NULL); 1284 if (error != 0) 1285 return (error); 1286 sdp = dvp->v_data; 1287 1288 mutex_enter(&sdp->sd_lock); 1289 1290 sep = avl_first(&sdp->sd_snaps); 1291 while (sep != NULL) { 1292 next = AVL_NEXT(&sdp->sd_snaps, sep); 1293 1294 /* 1295 * If this snapshot is not mounted, then it must 1296 * have just been unmounted by somebody else, and 1297 * will be cleaned up by zfsctl_snapdir_inactive(). 1298 */ 1299 if (vn_ismntpt(sep->se_root)) { 1300 avl_remove(&sdp->sd_snaps, sep); 1301 error = zfsctl_unmount_snap(sep, fflags, cr); 1302 if (error) { 1303 avl_add(&sdp->sd_snaps, sep); 1304 break; 1305 } 1306 } 1307 sep = next; 1308 } 1309 1310 mutex_exit(&sdp->sd_lock); 1311 VN_RELE(dvp); 1312 1313 return (error); 1314 } 1315