]> granicus.if.org Git - zfs/commitdiff
Fix i_flags issue caused by 64c688d
authorChunwei Chen <david.chen@osnexus.com>
Wed, 14 Dec 2016 22:18:53 +0000 (14:18 -0800)
committerChunwei Chen <david.chen@osnexus.com>
Wed, 14 Dec 2016 22:48:09 +0000 (14:48 -0800)
Fix zfs_xvattr_set to set S_IMMUTABLE and S_APPEND flags correctly.

Reinstate zfs_set_inode_flags and use it when zfs_xvatter_set and also when
setting up inode in zfs_znode_alloc and zfs_rezget.

Signed-off-by: Chunwei Chen <david.chen@osnexus.com>
module/zfs/zfs_znode.c

index 624e926961483cce4da705eb0e1fc1172e46e5ec..e87e6d216f5c874fd07312990a57aa089ff3c365 100644 (file)
@@ -479,6 +479,25 @@ zfs_inode_set_ops(zfs_sb_t *zsb, struct inode *ip)
        }
 }
 
+void
+zfs_set_inode_flags(znode_t *zp, struct inode *ip)
+{
+       /*
+        * Linux and Solaris have different sets of file attributes, so we
+        * restrict this conversion to the intersection of the two.
+        */
+
+       if (zp->z_pflags & ZFS_IMMUTABLE)
+               ip->i_flags |= S_IMMUTABLE;
+       else
+               ip->i_flags &= ~S_IMMUTABLE;
+
+       if (zp->z_pflags & ZFS_APPENDONLY)
+               ip->i_flags |= S_APPEND;
+       else
+               ip->i_flags &= ~S_APPEND;
+}
+
 /*
  * Update the embedded inode given the znode.  We should work toward
  * eliminating this function as soon as possible by removing values
@@ -588,6 +607,7 @@ zfs_znode_alloc(zfs_sb_t *zsb, dmu_buf_t *db, int blksz,
        set_nlink(ip, (uint32_t)links);
        zfs_uid_write(ip, z_uid);
        zfs_gid_write(ip, z_gid);
+       zfs_set_inode_flags(zp, ip);
 
        /* Cache the xattr parent id */
        if (zp->z_pflags & ZFS_XATTR)
@@ -918,6 +938,7 @@ void
 zfs_xvattr_set(znode_t *zp, xvattr_t *xvap, dmu_tx_t *tx)
 {
        xoptattr_t *xoap;
+       boolean_t update_inode = B_FALSE;
 
        xoap = xva_getxoptattr(xvap);
        ASSERT(xoap);
@@ -929,7 +950,6 @@ zfs_xvattr_set(znode_t *zp, xvattr_t *xvap, dmu_tx_t *tx)
                    &times, sizeof (times), tx);
                XVA_SET_RTN(xvap, XAT_CREATETIME);
        }
-
        if (XVA_ISSET_REQ(xvap, XAT_READONLY)) {
                ZFS_ATTR_SET(zp, ZFS_READONLY, xoap->xoa_readonly,
                    zp->z_pflags, tx);
@@ -955,11 +975,8 @@ zfs_xvattr_set(znode_t *zp, xvattr_t *xvap, dmu_tx_t *tx)
                    zp->z_pflags, tx);
                XVA_SET_RTN(xvap, XAT_IMMUTABLE);
 
-               ZTOI(zp)->i_flags |= S_IMMUTABLE;
-       } else {
-               ZTOI(zp)->i_flags &= ~S_IMMUTABLE;
+               update_inode = B_TRUE;
        }
-
        if (XVA_ISSET_REQ(xvap, XAT_NOUNLINK)) {
                ZFS_ATTR_SET(zp, ZFS_NOUNLINK, xoap->xoa_nounlink,
                    zp->z_pflags, tx);
@@ -970,12 +987,8 @@ zfs_xvattr_set(znode_t *zp, xvattr_t *xvap, dmu_tx_t *tx)
                    zp->z_pflags, tx);
                XVA_SET_RTN(xvap, XAT_APPENDONLY);
 
-               ZTOI(zp)->i_flags |= S_APPEND;
-       } else {
-
-               ZTOI(zp)->i_flags &= ~S_APPEND;
+               update_inode = B_TRUE;
        }
-
        if (XVA_ISSET_REQ(xvap, XAT_NODUMP)) {
                ZFS_ATTR_SET(zp, ZFS_NODUMP, xoap->xoa_nodump,
                    zp->z_pflags, tx);
@@ -1015,6 +1028,9 @@ zfs_xvattr_set(znode_t *zp, xvattr_t *xvap, dmu_tx_t *tx)
                    zp->z_pflags, tx);
                XVA_SET_RTN(xvap, XAT_SPARSE);
        }
+
+       if (update_inode)
+               zfs_set_inode_flags(zp, ZTOI(zp));
 }
 
 int
@@ -1220,12 +1236,12 @@ zfs_rezget(znode_t *zp)
 
        zp->z_unlinked = (ZTOI(zp)->i_nlink == 0);
        set_nlink(ZTOI(zp), (uint32_t)links);
+       zfs_set_inode_flags(zp, ZTOI(zp));
 
        zp->z_blksz = doi.doi_data_block_size;
        zp->z_atime_dirty = 0;
        zfs_inode_update(zp);
 
-
        zfs_znode_hold_exit(zsb, zh);
 
        return (0);