Unverified Commit a8292867 authored by openeuler-ci-bot's avatar openeuler-ci-bot Committed by Gitee
Browse files

!12689 ocfs2: reserve space for inline xattr before attaching reflink tree

parents f5bfb164 2b1b029a
Loading
Loading
Loading
Loading
+24 −2
Original line number Diff line number Diff line
@@ -27,6 +27,7 @@
#include "namei.h"
#include "ocfs2_trace.h"
#include "file.h"
#include "symlink.h"

#include <linux/bio.h>
#include <linux/blkdev.h>
@@ -4184,8 +4185,9 @@ static int __ocfs2_reflink(struct dentry *old_dentry,
	int ret;
	struct inode *inode = d_inode(old_dentry);
	struct buffer_head *new_bh = NULL;
	struct ocfs2_inode_info *oi = OCFS2_I(inode);

	if (OCFS2_I(inode)->ip_flags & OCFS2_INODE_SYSTEM_FILE) {
	if (oi->ip_flags & OCFS2_INODE_SYSTEM_FILE) {
		ret = -EINVAL;
		mlog_errno(ret);
		goto out;
@@ -4211,6 +4213,26 @@ static int __ocfs2_reflink(struct dentry *old_dentry,
		goto out_unlock;
	}

	if ((oi->ip_dyn_features & OCFS2_HAS_XATTR_FL) &&
	    (oi->ip_dyn_features & OCFS2_INLINE_XATTR_FL)) {
		/*
		 * Adjust extent record count to reserve space for extended attribute.
		 * Inline data count had been adjusted in ocfs2_duplicate_inline_data().
		 */
		struct ocfs2_inode_info *new_oi = OCFS2_I(new_inode);

		if (!(new_oi->ip_dyn_features & OCFS2_INLINE_DATA_FL) &&
		    !(ocfs2_inode_is_fast_symlink(new_inode))) {
			struct ocfs2_dinode *new_di = (struct ocfs2_dinode *)new_bh->b_data;
			struct ocfs2_dinode *old_di = (struct ocfs2_dinode *)old_bh->b_data;
			struct ocfs2_extent_list *el = &new_di->id2.i_list;
			int inline_size = le16_to_cpu(old_di->i_xattr_inline_size);

			le16_add_cpu(&el->l_count, -(inline_size /
					sizeof(struct ocfs2_extent_rec)));
		}
	}

	ret = ocfs2_create_reflink_node(inode, old_bh,
					new_inode, new_bh, preserve);
	if (ret) {
@@ -4218,7 +4240,7 @@ static int __ocfs2_reflink(struct dentry *old_dentry,
		goto inode_unlock;
	}

	if (OCFS2_I(inode)->ip_dyn_features & OCFS2_HAS_XATTR_FL) {
	if (oi->ip_dyn_features & OCFS2_HAS_XATTR_FL) {
		ret = ocfs2_reflink_xattrs(inode, old_bh,
					   new_inode, new_bh,
					   preserve);
+1 −10
Original line number Diff line number Diff line
@@ -6526,16 +6526,7 @@ static int ocfs2_reflink_xattr_inline(struct ocfs2_xattr_reflink *args)
	}

	new_oi = OCFS2_I(args->new_inode);
	/*
	 * Adjust extent record count to reserve space for extended attribute.
	 * Inline data count had been adjusted in ocfs2_duplicate_inline_data().
	 */
	if (!(new_oi->ip_dyn_features & OCFS2_INLINE_DATA_FL) &&
	    !(ocfs2_inode_is_fast_symlink(args->new_inode))) {
		struct ocfs2_extent_list *el = &new_di->id2.i_list;
		le16_add_cpu(&el->l_count, -(inline_size /
					sizeof(struct ocfs2_extent_rec)));
	}

	spin_lock(&new_oi->ip_lock);
	new_oi->ip_dyn_features |= OCFS2_HAS_XATTR_FL | OCFS2_INLINE_XATTR_FL;
	new_di->i_dyn_features = cpu_to_le16(new_oi->ip_dyn_features);