Commit 370e55ac authored by Miklos Szeredi's avatar Miklos Szeredi

ovl: rename: simplify handling of lower/merged directory

d_is_dir() is safe to call on a negative dentry.  Use this fact to simplify
handling of the lower or merged directories.
Signed-off-by: default avatarMiklos Szeredi <mszeredi@redhat.com>
parent 38e813db
...@@ -761,13 +761,18 @@ static int ovl_rmdir(struct inode *dir, struct dentry *dentry) ...@@ -761,13 +761,18 @@ static int ovl_rmdir(struct inode *dir, struct dentry *dentry)
return ovl_do_remove(dentry, true); return ovl_do_remove(dentry, true);
} }
static bool ovl_type_merge_or_lower(struct dentry *dentry)
{
enum ovl_path_type type = ovl_path_type(dentry);
return OVL_TYPE_MERGE(type) || !OVL_TYPE_UPPER(type);
}
static int ovl_rename(struct inode *olddir, struct dentry *old, static int ovl_rename(struct inode *olddir, struct dentry *old,
struct inode *newdir, struct dentry *new, struct inode *newdir, struct dentry *new,
unsigned int flags) unsigned int flags)
{ {
int err; int err;
enum ovl_path_type old_type;
enum ovl_path_type new_type;
struct dentry *old_upperdir; struct dentry *old_upperdir;
struct dentry *new_upperdir; struct dentry *new_upperdir;
struct dentry *olddentry; struct dentry *olddentry;
...@@ -778,7 +783,7 @@ static int ovl_rename(struct inode *olddir, struct dentry *old, ...@@ -778,7 +783,7 @@ static int ovl_rename(struct inode *olddir, struct dentry *old,
bool cleanup_whiteout = false; bool cleanup_whiteout = false;
bool overwrite = !(flags & RENAME_EXCHANGE); bool overwrite = !(flags & RENAME_EXCHANGE);
bool is_dir = d_is_dir(old); bool is_dir = d_is_dir(old);
bool new_is_dir = false; bool new_is_dir = d_is_dir(new);
struct dentry *opaquedir = NULL; struct dentry *opaquedir = NULL;
const struct cred *old_cred = NULL; const struct cred *old_cred = NULL;
...@@ -789,22 +794,11 @@ static int ovl_rename(struct inode *olddir, struct dentry *old, ...@@ -789,22 +794,11 @@ static int ovl_rename(struct inode *olddir, struct dentry *old,
flags &= ~RENAME_NOREPLACE; flags &= ~RENAME_NOREPLACE;
/* Don't copy up directory trees */ /* Don't copy up directory trees */
old_type = ovl_path_type(old);
err = -EXDEV; err = -EXDEV;
if (OVL_TYPE_MERGE_OR_LOWER(old_type) && is_dir) if (is_dir && ovl_type_merge_or_lower(old))
goto out;
if (!overwrite && new_is_dir && ovl_type_merge_or_lower(new))
goto out; goto out;
if (new->d_inode) {
if (d_is_dir(new))
new_is_dir = true;
new_type = ovl_path_type(new);
err = -EXDEV;
if (!overwrite && OVL_TYPE_MERGE_OR_LOWER(new_type) && new_is_dir)
goto out;
} else {
new_type = __OVL_PATH_UPPER;
}
err = ovl_want_write(old); err = ovl_want_write(old);
if (err) if (err)
...@@ -828,7 +822,7 @@ static int ovl_rename(struct inode *olddir, struct dentry *old, ...@@ -828,7 +822,7 @@ static int ovl_rename(struct inode *olddir, struct dentry *old,
old_cred = ovl_override_creds(old->d_sb); old_cred = ovl_override_creds(old->d_sb);
if (overwrite && OVL_TYPE_MERGE_OR_LOWER(new_type) && new_is_dir) { if (overwrite && new_is_dir && ovl_type_merge_or_lower(new)) {
opaquedir = ovl_check_empty_and_clear(new); opaquedir = ovl_check_empty_and_clear(new);
err = PTR_ERR(opaquedir); err = PTR_ERR(opaquedir);
if (IS_ERR(opaquedir)) { if (IS_ERR(opaquedir)) {
......
...@@ -18,9 +18,6 @@ enum ovl_path_type { ...@@ -18,9 +18,6 @@ enum ovl_path_type {
#define OVL_TYPE_UPPER(type) ((type) & __OVL_PATH_UPPER) #define OVL_TYPE_UPPER(type) ((type) & __OVL_PATH_UPPER)
#define OVL_TYPE_MERGE(type) ((type) & __OVL_PATH_MERGE) #define OVL_TYPE_MERGE(type) ((type) & __OVL_PATH_MERGE)
#define OVL_TYPE_MERGE_OR_LOWER(type) \
(OVL_TYPE_MERGE(type) || !OVL_TYPE_UPPER(type))
#define OVL_XATTR_PREFIX XATTR_TRUSTED_PREFIX "overlay." #define OVL_XATTR_PREFIX XATTR_TRUSTED_PREFIX "overlay."
#define OVL_XATTR_OPAQUE OVL_XATTR_PREFIX "opaque" #define OVL_XATTR_OPAQUE OVL_XATTR_PREFIX "opaque"
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment