]> granicus.if.org Git - zfs/commitdiff
Illumos #3973
authorSteven Hartland <smh@freebsd.org>
Tue, 6 Aug 2013 17:50:40 +0000 (09:50 -0800)
committerBrian Behlendorf <behlendorf1@llnl.gov>
Tue, 5 Nov 2013 20:15:50 +0000 (12:15 -0800)
3973 zfs_ioc_rename alters passed in zc->zc_name
Reviewed by: Matthew Ahrens <mahrens@delphix.com>
Reviewed by: George Wilson <george.wilson@delphix.com>
Approved by: Christopher Siden <christopher.siden@delphix.com>

References:
  https://www.illumos.org/issues/3973
  illumos/illumos-gate@a0c1127b147dc6a0372b141deb8c0c2b0195b8ea

Ported-by: Richard Yao <ryao@gentoo.org>
Signed-off-by: Brian Behlendorf <behlendorf1@llnl.gov>
Issue #1775

module/zfs/zfs_ioctl.c

index 556a0c94037ddcce386f49eca31b18451654dfde..4ad885ac65cea3bd3b590d228e52ca7db9d9e80d 100644 (file)
@@ -3550,18 +3550,25 @@ zfs_ioc_rename(zfs_cmd_t *zc)
        at = strchr(zc->zc_name, '@');
        if (at != NULL) {
                /* snaps must be in same fs */
+               int error;
+
                if (strncmp(zc->zc_name, zc->zc_value, at - zc->zc_name + 1))
                        return (SET_ERROR(EXDEV));
                *at = '\0';
                if (zc->zc_objset_type == DMU_OST_ZFS) {
-                       int error = dmu_objset_find(zc->zc_name,
+                       error = dmu_objset_find(zc->zc_name,
                            recursive_unmount, at + 1,
                            recursive ? DS_FIND_CHILDREN : 0);
-                       if (error != 0)
+                       if (error != 0) {
+                               *at = '@';
                                return (error);
+                       }
                }
-               return (dsl_dataset_rename_snapshot(zc->zc_name,
-                   at + 1, strchr(zc->zc_value, '@') + 1, recursive));
+               error = dsl_dataset_rename_snapshot(zc->zc_name,
+                   at + 1, strchr(zc->zc_value, '@') + 1, recursive);
+               *at = '@';
+
+               return (error);
        } else {
                err = dsl_dir_rename(zc->zc_name, zc->zc_value);
                if (!err && zc->zc_objset_type == DMU_OST_ZVOL) {