Merge branch 'work.xattr' of git://git.kernel.org/pub/scm/linux/kernel/git/viro/vfs
[cascardo/linux.git] / drivers / staging / lustre / lustre / llite / file.c
index ce96c9f..e1d784b 100644 (file)
 #include <linux/file.h>
 #include <linux/sched.h>
 #include <linux/mount.h>
-#include "llite_internal.h"
 #include "../include/lustre/ll_fiemap.h"
 #include "../include/lustre/lustre_ioctl.h"
 
 #include "../include/cl_object.h"
+#include "llite_internal.h"
 
 static int
 ll_put_grouplock(struct inode *inode, struct file *file, unsigned long arg);
@@ -889,7 +889,6 @@ static int ll_lease_close(struct obd_client_handle *och, struct inode *inode,
 {
        struct ldlm_lock *lock;
        bool cancelled = true;
-       int rc;
 
        lock = ldlm_handle2lock(&och->och_lease_handle);
        if (lock) {
@@ -907,9 +906,8 @@ static int ll_lease_close(struct obd_client_handle *och, struct inode *inode,
        if (lease_broken)
                *lease_broken = cancelled;
 
-       rc = ll_close_inode_openhandle(ll_i2sbi(inode)->ll_md_exp, inode, och,
-                                      NULL);
-       return rc;
+       return ll_close_inode_openhandle(ll_i2sbi(inode)->ll_md_exp,
+                                        inode, och, NULL);
 }
 
 /* Fills the obdo with the attributes for the lsm */
@@ -1123,8 +1121,8 @@ ll_file_io_generic(const struct lu_env *env, struct vvp_io_args *args,
        struct cl_io     *io;
        ssize_t        result;
 
-       CDEBUG(D_VFSTRACE, "file: %s, type: %d ppos: %llu, count: %zu\n",
-              file->f_path.dentry->d_name.name, iot, *ppos, count);
+       CDEBUG(D_VFSTRACE, "file: %pD, type: %d ppos: %llu, count: %zu\n",
+              file, iot, *ppos, count);
 
 restart:
        io = vvp_env_thread_io(env);
@@ -1140,45 +1138,31 @@ restart:
                        range_lock_init(&range, *ppos, *ppos + count - 1);
 
                vio->vui_fd  = LUSTRE_FPRIVATE(file);
-               vio->vui_io_subtype = args->via_io_subtype;
+               vio->vui_iter = args->u.normal.via_iter;
+               vio->vui_iocb = args->u.normal.via_iocb;
+               /*
+                * Direct IO reads must also take range lock,
+                * or multiple reads will try to work on the same pages
+                * See LU-6227 for details.
+                */
+               if (((iot == CIT_WRITE) ||
+                    (iot == CIT_READ && (file->f_flags & O_DIRECT))) &&
+                   !(vio->vui_fd->fd_flags & LL_FILE_GROUP_LOCKED)) {
+                       CDEBUG(D_VFSTRACE, "Range lock [%llu, %llu]\n",
+                              range.rl_node.in_extent.start,
+                              range.rl_node.in_extent.end);
+                       result = range_lock(&lli->lli_write_tree,
+                                           &range);
+                       if (result < 0)
+                               goto out;
 
-               switch (vio->vui_io_subtype) {
-               case IO_NORMAL:
-                       vio->vui_iter = args->u.normal.via_iter;
-                       vio->vui_iocb = args->u.normal.via_iocb;
-                       /*
-                        * Direct IO reads must also take range lock,
-                        * or multiple reads will try to work on the same pages
-                        * See LU-6227 for details.
-                        */
-                       if (((iot == CIT_WRITE) ||
-                            (iot == CIT_READ && (file->f_flags & O_DIRECT))) &&
-                           !(vio->vui_fd->fd_flags & LL_FILE_GROUP_LOCKED)) {
-                               CDEBUG(D_VFSTRACE, "Range lock [%llu, %llu]\n",
-                                      range.rl_node.in_extent.start,
-                                      range.rl_node.in_extent.end);
-                               result = range_lock(&lli->lli_write_tree,
-                                                   &range);
-                               if (result < 0)
-                                       goto out;
-
-                               range_locked = true;
-                       }
-                       down_read(&lli->lli_trunc_sem);
-                       break;
-               case IO_SPLICE:
-                       vio->u.splice.vui_pipe = args->u.splice.via_pipe;
-                       vio->u.splice.vui_flags = args->u.splice.via_flags;
-                       break;
-               default:
-                       CERROR("Unknown IO type - %u\n", vio->vui_io_subtype);
-                       LBUG();
+                       range_locked = true;
                }
+               down_read(&lli->lli_trunc_sem);
                ll_cl_add(file, env, io);
                result = cl_io_loop(env, io);
                ll_cl_remove(file, env);
-               if (args->via_io_subtype == IO_NORMAL)
-                       up_read(&lli->lli_trunc_sem);
+               up_read(&lli->lli_trunc_sem);
                if (range_locked) {
                        CDEBUG(D_VFSTRACE, "Range unlock [%llu, %llu]\n",
                               range.rl_node.in_extent.start,
@@ -1237,7 +1221,7 @@ static ssize_t ll_file_read_iter(struct kiocb *iocb, struct iov_iter *to)
        if (IS_ERR(env))
                return PTR_ERR(env);
 
-       args = ll_env_args(env, IO_NORMAL);
+       args = ll_env_args(env);
        args->u.normal.via_iter = to;
        args->u.normal.via_iocb = iocb;
 
@@ -1261,7 +1245,7 @@ static ssize_t ll_file_write_iter(struct kiocb *iocb, struct iov_iter *from)
        if (IS_ERR(env))
                return PTR_ERR(env);
 
-       args = ll_env_args(env, IO_NORMAL);
+       args = ll_env_args(env);
        args->u.normal.via_iter = from;
        args->u.normal.via_iocb = iocb;
 
@@ -1271,31 +1255,6 @@ static ssize_t ll_file_write_iter(struct kiocb *iocb, struct iov_iter *from)
        return result;
 }
 
-/*
- * Send file content (through pagecache) somewhere with helper
- */
-static ssize_t ll_file_splice_read(struct file *in_file, loff_t *ppos,
-                                  struct pipe_inode_info *pipe, size_t count,
-                                  unsigned int flags)
-{
-       struct lu_env      *env;
-       struct vvp_io_args *args;
-       ssize_t      result;
-       int              refcheck;
-
-       env = cl_env_get(&refcheck);
-       if (IS_ERR(env))
-               return PTR_ERR(env);
-
-       args = ll_env_args(env, IO_SPLICE);
-       args->u.splice.via_pipe = pipe;
-       args->u.splice.via_flags = flags;
-
-       result = ll_file_io_generic(env, args, in_file, CIT_READ, ppos, count);
-       cl_env_put(env, &refcheck);
-       return result;
-}
-
 int ll_lov_setstripe_ea_info(struct inode *inode, struct dentry *dentry,
                             __u64 flags, struct lov_user_md *lum,
                             int lum_size)
@@ -2489,9 +2448,8 @@ static loff_t ll_file_seek(struct file *file, loff_t offset, int origin)
                eof = i_size_read(inode);
        }
 
-       retval = generic_file_llseek_size(file, offset, origin,
-                                         ll_file_maxbytes(inode), eof);
-       return retval;
+       return generic_file_llseek_size(file, offset, origin,
+                                       ll_file_maxbytes(inode), eof);
 }
 
 static int ll_flush(struct file *file, fl_owner_t id)
@@ -2802,11 +2760,15 @@ int ll_migrate(struct inode *parent, struct file *file, int mdtidx,
        qstr.name = name;
        qstr.len = namelen;
        dchild = d_lookup(file_dentry(file), &qstr);
-       if (dchild && dchild->d_inode) {
+       if (dchild) {
                op_data->op_fid3 = *ll_inode2fid(dchild->d_inode);
                if (dchild->d_inode) {
                        child_inode = igrab(dchild->d_inode);
-                       ll_invalidate_aliases(child_inode);
+                       if (child_inode) {
+                               inode_lock(child_inode);
+                               op_data->op_fid3 = *ll_inode2fid(child_inode);
+                               ll_invalidate_aliases(child_inode);
+                       }
                }
                dput(dchild);
        } else {
@@ -2847,6 +2809,7 @@ int ll_migrate(struct inode *parent, struct file *file, int mdtidx,
 out_free:
        if (child_inode) {
                clear_nlink(child_inode);
+               inode_unlock(child_inode);
                iput(child_inode);
        }
 
@@ -2917,15 +2880,12 @@ enum ldlm_mode ll_take_md_lock(struct inode *inode, __u64 bits,
 {
        ldlm_policy_data_t policy = { .l_inodebits = {bits} };
        struct lu_fid *fid;
-       enum ldlm_mode rc;
 
        fid = &ll_i2info(inode)->lli_fid;
        CDEBUG(D_INFO, "trying to match res "DFID"\n", PFID(fid));
 
-       rc = md_lock_match(ll_i2mdexp(inode), flags | LDLM_FL_BLOCK_GRANTED,
-                          fid, LDLM_IBITS, &policy, mode, lockh);
-
-       return rc;
+       return md_lock_match(ll_i2mdexp(inode), flags | LDLM_FL_BLOCK_GRANTED,
+                            fid, LDLM_IBITS, &policy, mode, lockh);
 }
 
 static int ll_inode_revalidate_fini(struct inode *inode, int rc)
@@ -3026,10 +2986,8 @@ static int __ll_inode_revalidate(struct dentry *dentry, __u64 ibits)
                op_data->op_valid = valid;
                rc = md_getattr(sbi->ll_md_exp, op_data, &req);
                ll_finish_md_op_data(op_data);
-               if (rc) {
-                       rc = ll_inode_revalidate_fini(inode, rc);
-                       return rc;
-               }
+               if (rc)
+                       return ll_inode_revalidate_fini(inode, rc);
 
                rc = ll_prep_inode(&inode, req, NULL, NULL);
        }
@@ -3045,12 +3003,13 @@ static int ll_merge_md_attr(struct inode *inode)
 
        LASSERT(ll_i2info(inode)->lli_lsm_md);
        rc = md_merge_attr(ll_i2mdexp(inode), ll_i2info(inode)->lli_lsm_md,
-                          &attr);
+                          &attr, ll_md_blocking_ast);
        if (rc)
                return rc;
 
-       ll_i2info(inode)->lli_stripe_dir_size = attr.cat_size;
-       ll_i2info(inode)->lli_stripe_dir_nlink = attr.cat_nlink;
+       set_nlink(inode, attr.cat_nlink);
+       inode->i_blocks = attr.cat_blocks;
+       i_size_write(inode, attr.cat_size);
 
        ll_i2info(inode)->lli_atime = attr.cat_atime;
        ll_i2info(inode)->lli_mtime = attr.cat_mtime;
@@ -3123,16 +3082,10 @@ int ll_getattr(struct vfsmount *mnt, struct dentry *de, struct kstat *stat)
        stat->mtime = inode->i_mtime;
        stat->ctime = inode->i_ctime;
        stat->blksize = 1 << inode->i_blkbits;
-       stat->blocks = inode->i_blocks;
 
-       if (S_ISDIR(inode->i_mode) &&
-           ll_i2info(inode)->lli_lsm_md) {
-               stat->nlink = lli->lli_stripe_dir_nlink;
-               stat->size = lli->lli_stripe_dir_size;
-       } else {
-               stat->nlink = inode->i_nlink;
-               stat->size = i_size_read(inode);
-       }
+       stat->nlink = inode->i_nlink;
+       stat->size = i_size_read(inode);
+       stat->blocks = inode->i_blocks;
 
        return 0;
 }
@@ -3275,7 +3228,7 @@ struct file_operations ll_file_operations = {
        .release        = ll_file_release,
        .mmap      = ll_file_mmap,
        .llseek  = ll_file_seek,
-       .splice_read    = ll_file_splice_read,
+       .splice_read    = generic_file_splice_read,
        .fsync    = ll_fsync,
        .flush    = ll_flush
 };
@@ -3288,7 +3241,7 @@ struct file_operations ll_file_operations_flock = {
        .release        = ll_file_release,
        .mmap      = ll_file_mmap,
        .llseek  = ll_file_seek,
-       .splice_read    = ll_file_splice_read,
+       .splice_read    = generic_file_splice_read,
        .fsync    = ll_fsync,
        .flush    = ll_flush,
        .flock    = ll_file_flock,
@@ -3304,7 +3257,7 @@ struct file_operations ll_file_operations_noflock = {
        .release        = ll_file_release,
        .mmap      = ll_file_mmap,
        .llseek  = ll_file_seek,
-       .splice_read    = ll_file_splice_read,
+       .splice_read    = generic_file_splice_read,
        .fsync    = ll_fsync,
        .flush    = ll_flush,
        .flock    = ll_file_noflock,
@@ -3315,10 +3268,7 @@ const struct inode_operations ll_file_inode_operations = {
        .setattr        = ll_setattr,
        .getattr        = ll_getattr,
        .permission     = ll_inode_permission,
-       .setxattr       = generic_setxattr,
-       .getxattr       = generic_getxattr,
        .listxattr      = ll_listxattr,
-       .removexattr    = generic_removexattr,
        .fiemap         = ll_fiemap,
        .get_acl        = ll_get_acl,
 };