Ack: [PATCH 1/1] eCryptfs: Copy up attributes of the lower target inode after rename

Brad Figg brad.figg at canonical.com
Sun Sep 16 06:07:26 UTC 2012


On 09/15/2012 12:10 PM, Colin King wrote:
> From: Tyler Hicks <tyhicks at canonical.com>
> 
> After calling into the lower filesystem to do a rename, the lower target
> inode's attributes were not copied up to the eCryptfs target inode. This
> resulted in the eCryptfs target inode staying around, rather than being
> evicted, because i_nlink was not updated for the eCryptfs inode. This
> also meant that eCryptfs didn't do the final iput() on the lower target
> inode so it stayed around, as well. This would result in a failure to
> free up space occupied by the target file in the rename() operation.
> Both target inodes would eventually be evicted when the eCryptfs
> filesystem was unmounted.
> 
> This patch calls fsstack_copy_attr_all() after the lower filesystem
> does its ->rename() so that important inode attributes, such as i_nlink,
> are updated at the eCryptfs layer. ecryptfs_evict_inode() is now called
> and eCryptfs can drop its final reference on the lower inode.
> 
> BugLink: http://launchpad.net/bugs/561129
> 
> Signed-off-by: Tyler Hicks <tyhicks at canonical.com>
> Tested-by: Colin Ian King <colin.king at canonical.com>
> Cc: <stable at vger.kernel.org> [2.6.39+]
> (upstream cherry pick 8335eafc2859e1a26282bef7c3d19f3d68868b8a)
> Signed-off-by: Colin Ian King <colin.king at canonical.com>
> ---
>  fs/ecryptfs/inode.c |    5 +++++
>  1 file changed, 5 insertions(+)
> 
> diff --git a/fs/ecryptfs/inode.c b/fs/ecryptfs/inode.c
> index 534b129..cc7709e 100644
> --- a/fs/ecryptfs/inode.c
> +++ b/fs/ecryptfs/inode.c
> @@ -619,6 +619,7 @@ ecryptfs_rename(struct inode *old_dir, struct dentry *old_dentry,
>  	struct dentry *lower_old_dir_dentry;
>  	struct dentry *lower_new_dir_dentry;
>  	struct dentry *trap = NULL;
> +	struct inode *target_inode;
>  
>  	lower_old_dentry = ecryptfs_dentry_to_lower(old_dentry);
>  	lower_new_dentry = ecryptfs_dentry_to_lower(new_dentry);
> @@ -626,6 +627,7 @@ ecryptfs_rename(struct inode *old_dir, struct dentry *old_dentry,
>  	dget(lower_new_dentry);
>  	lower_old_dir_dentry = dget_parent(lower_old_dentry);
>  	lower_new_dir_dentry = dget_parent(lower_new_dentry);
> +	target_inode = new_dentry->d_inode;
>  	trap = lock_rename(lower_old_dir_dentry, lower_new_dir_dentry);
>  	/* source should not be ancestor of target */
>  	if (trap == lower_old_dentry) {
> @@ -641,6 +643,9 @@ ecryptfs_rename(struct inode *old_dir, struct dentry *old_dentry,
>  			lower_new_dir_dentry->d_inode, lower_new_dentry);
>  	if (rc)
>  		goto out_lock;
> +	if (target_inode)
> +		fsstack_copy_attr_all(target_inode,
> +				      ecryptfs_inode_to_lower(target_inode));
>  	fsstack_copy_attr_all(new_dir, lower_new_dir_dentry->d_inode);
>  	if (new_dir != old_dir)
>  		fsstack_copy_attr_all(old_dir, lower_old_dir_dentry->d_inode);
> 


-- 
Brad Figg brad.figg at canonical.com http://www.canonical.com




More information about the kernel-team mailing list