BACKPORT: block/loop: set hw_sectors
[GitHub/exynos8895/android_kernel_samsung_universal8895.git] / fs / namei.c
index f8eeea95650395d33be8697250fe90007e307507..16fd94702e158b22c8a5dc81d58672e4c3d65af7 100644 (file)
@@ -1081,13 +1081,21 @@ int follow_up(struct path *path)
                read_sequnlock_excl(&mount_lock);
                return 0;
        }
+#ifdef CONFIG_RKP_NS_PROT
+       mntget(parent->mnt);
+#else
        mntget(&parent->mnt);
+#endif
        mountpoint = dget(mnt->mnt_mountpoint);
        read_sequnlock_excl(&mount_lock);
        dput(path->dentry);
        path->dentry = mountpoint;
        mntput(path->mnt);
+#ifdef CONFIG_RKP_NS_PROT
+       path->mnt = parent->mnt;
+#else
        path->mnt = &parent->mnt;
+#endif
        return 1;
 }
 EXPORT_SYMBOL(follow_up);
@@ -1293,8 +1301,13 @@ static bool __follow_mount_rcu(struct nameidata *nd, struct path *path,
                mounted = __lookup_mnt(path->mnt, path->dentry);
                if (!mounted)
                        break;
+#ifdef CONFIG_RKP_NS_PROT
+               path->mnt = mounted->mnt;
+               path->dentry = mounted->mnt->mnt_root;
+#else
                path->mnt = &mounted->mnt;
                path->dentry = mounted->mnt.mnt_root;
+#endif
                nd->flags |= LOOKUP_JUMPED;
                *seqp = read_seqcount_begin(&path->dentry->d_seq);
                /*
@@ -1339,11 +1352,19 @@ static int follow_dotdot_rcu(struct nameidata *nd)
                        unsigned seq = read_seqcount_begin(&mountpoint->d_seq);
                        if (unlikely(read_seqretry(&mount_lock, nd->m_seq)))
                                return -ECHILD;
+#ifdef CONFIG_RKP_NS_PROT
+                       if (mparent->mnt == nd->path.mnt)
+#else
                        if (&mparent->mnt == nd->path.mnt)
+#endif
                                break;
                        /* we know that mountpoint was pinned */
                        nd->path.dentry = mountpoint;
+#ifdef CONFIG_RKP_NS_PROT
+                       nd->path.mnt = mparent->mnt;
+#else
                        nd->path.mnt = &mparent->mnt;
+#endif
                        inode = inode2;
                        nd->seq = seq;
                }
@@ -1355,8 +1376,13 @@ static int follow_dotdot_rcu(struct nameidata *nd)
                        return -ECHILD;
                if (!mounted)
                        break;
+#ifdef CONFIG_RKP_NS_PROT
+               nd->path.mnt = mounted->mnt;
+               nd->path.dentry = mounted->mnt->mnt_root;
+#else
                nd->path.mnt = &mounted->mnt;
                nd->path.dentry = mounted->mnt.mnt_root;
+#endif
                inode = nd->path.dentry->d_inode;
                nd->seq = read_seqcount_begin(&nd->path.dentry->d_seq);
        }
@@ -3592,10 +3618,10 @@ retry:
                goto out;
        switch (mode & S_IFMT) {
                case 0: case S_IFREG:
-                       error = vfs_create2(path.mnt, path.dentry->d_inode,dentry,mode,true);
+                       error = vfs_create2(path.mnt, path.dentry->d_inode, dentry, mode, true);
                        break;
                case S_IFCHR: case S_IFBLK:
-                       error = vfs_mknod2(path.mnt, path.dentry->d_inode,dentry,mode,
+                       error = vfs_mknod2(path.mnt, path.dentry->d_inode, dentry, mode,
                                        new_decode_dev(dev));
                        break;
                case S_IFIFO: case S_IFSOCK:
@@ -3740,8 +3766,6 @@ out:
                d_delete(dentry);
        return error;
 }
-EXPORT_SYMBOL(vfs_rmdir2);
-
 int vfs_rmdir(struct inode *dir, struct dentry *dentry)
 {
        return vfs_rmdir2(NULL, dir, dentry);
@@ -3757,6 +3781,8 @@ static long do_rmdir(int dfd, const char __user *pathname)
        struct qstr last;
        int type;
        unsigned int lookup_flags = 0;
+       char *path_buf = NULL;
+       char *propagate_path = NULL;
 retry:
        name = user_path_parent(dfd, pathname,
                                &path, &last, &type, lookup_flags);
@@ -3791,11 +3817,26 @@ retry:
        error = security_path_rmdir(&path, dentry);
        if (error)
                goto exit3;
+       if (dentry->d_sb->s_op->unlink_callback) {
+               path_buf = kmalloc(PATH_MAX, GFP_KERNEL);
+               propagate_path = dentry_path_raw(dentry, path_buf, PATH_MAX);
+       }
        error = vfs_rmdir2(path.mnt, path.dentry->d_inode, dentry);
+#ifdef CONFIG_PROC_DLOG
+       if (!error)
+               dlog_hook_rmdir(dentry, &path);
+#endif
 exit3:
        dput(dentry);
 exit2:
        mutex_unlock(&path.dentry->d_inode->i_mutex);
+       if (path_buf && !error) {
+               path.dentry->d_sb->s_op->unlink_callback(path.dentry->d_sb, propagate_path);
+       }
+       if (path_buf) {
+               kfree(path_buf);
+               path_buf = NULL;
+       }
        mnt_drop_write(path.mnt);
 exit1:
        path_put(&path);
@@ -3893,6 +3934,8 @@ static long do_unlinkat(int dfd, const char __user *pathname)
        struct inode *inode = NULL;
        struct inode *delegated_inode = NULL;
        unsigned int lookup_flags = 0;
+       char *path_buf = NULL;
+       char *propagate_path = NULL;
 retry:
        name = user_path_parent(dfd, pathname,
                                &path, &last, &type, lookup_flags);
@@ -3917,15 +3960,30 @@ retry_deleg:
                inode = dentry->d_inode;
                if (d_is_negative(dentry))
                        goto slashes;
+               if (inode->i_sb->s_op->unlink_callback) {
+                       path_buf = kmalloc(PATH_MAX, GFP_KERNEL);
+                       propagate_path = dentry_path_raw(dentry, path_buf, PATH_MAX);
+               }
                ihold(inode);
                error = security_path_unlink(&path, dentry);
                if (error)
                        goto exit2;
                error = vfs_unlink2(path.mnt, path.dentry->d_inode, dentry, &delegated_inode);
+#ifdef CONFIG_PROC_DLOG
+               if (!error)
+                       dlog_hook(dentry, inode, &path);
+#endif
 exit2:
                dput(dentry);
        }
        mutex_unlock(&path.dentry->d_inode->i_mutex);
+       if (path_buf && !error) {
+               inode->i_sb->s_op->unlink_callback(inode->i_sb, propagate_path);
+       }
+       if (path_buf) {
+               kfree(path_buf);
+               path_buf = NULL;
+       }
        if (inode)
                iput(inode);    /* truncate the inode here */
        inode = NULL;