]> Pileus Git - ~andy/linux/blobdiff - fs/nfs/inode.c
ARM: cacheflush: don't bother rounding to nearest vma
[~andy/linux] / fs / nfs / inode.c
index 12e8ad85ae50103d5745339e472bc639ad8f8411..af6e806044d7cee5d8047a56de6693388fc8d34f 100644 (file)
@@ -48,7 +48,6 @@
 #include "iostat.h"
 #include "internal.h"
 #include "fscache.h"
-#include "dns_resolve.h"
 #include "pnfs.h"
 #include "nfs.h"
 #include "netns.h"
@@ -79,7 +78,7 @@ int nfs_wait_bit_killable(void *word)
 {
        if (fatal_signal_pending(current))
                return -ERESTARTSYS;
-       freezable_schedule();
+       freezable_schedule_unsafe();
        return 0;
 }
 EXPORT_SYMBOL_GPL(nfs_wait_bit_killable);
@@ -162,11 +161,19 @@ static void nfs_zap_caches_locked(struct inode *inode)
 
        memset(NFS_I(inode)->cookieverf, 0, sizeof(NFS_I(inode)->cookieverf));
        if (S_ISREG(mode) || S_ISDIR(mode) || S_ISLNK(mode)) {
-               nfsi->cache_validity |= NFS_INO_INVALID_ATTR|NFS_INO_INVALID_DATA|NFS_INO_INVALID_ACCESS|NFS_INO_INVALID_ACL|NFS_INO_REVAL_PAGECACHE;
                nfs_fscache_invalidate(inode);
-       } else {
-               nfsi->cache_validity |= NFS_INO_INVALID_ATTR|NFS_INO_INVALID_ACCESS|NFS_INO_INVALID_ACL|NFS_INO_REVAL_PAGECACHE;
-       }
+               nfsi->cache_validity |= NFS_INO_INVALID_ATTR
+                                       | NFS_INO_INVALID_LABEL
+                                       | NFS_INO_INVALID_DATA
+                                       | NFS_INO_INVALID_ACCESS
+                                       | NFS_INO_INVALID_ACL
+                                       | NFS_INO_REVAL_PAGECACHE;
+       } else
+               nfsi->cache_validity |= NFS_INO_INVALID_ATTR
+                                       | NFS_INO_INVALID_LABEL
+                                       | NFS_INO_INVALID_ACCESS
+                                       | NFS_INO_INVALID_ACL
+                                       | NFS_INO_REVAL_PAGECACHE;
 }
 
 void nfs_zap_caches(struct inode *inode)
@@ -258,6 +265,32 @@ nfs_init_locked(struct inode *inode, void *opaque)
 }
 
 #ifdef CONFIG_NFS_V4_SECURITY_LABEL
+void nfs_setsecurity(struct inode *inode, struct nfs_fattr *fattr,
+                                       struct nfs4_label *label)
+{
+       int error;
+
+       if (label == NULL)
+               return;
+
+       if (nfs_server_capable(inode, NFS_CAP_SECURITY_LABEL) == 0)
+               return;
+
+       if (NFS_SERVER(inode)->nfs_client->cl_minorversion < 2)
+               return;
+
+       if ((fattr->valid & NFS_ATTR_FATTR_V4_SECURITY_LABEL) && inode->i_security) {
+               error = security_inode_notifysecctx(inode, label->label,
+                               label->len);
+               if (error)
+                       printk(KERN_ERR "%s() %s %d "
+                                       "security_inode_notifysecctx() %d\n",
+                                       __func__,
+                                       (char *)label->label,
+                                       label->len, error);
+       }
+}
+
 struct nfs4_label *nfs4_label_alloc(struct nfs_server *server, gfp_t flags)
 {
        struct nfs4_label *label = NULL;
@@ -283,7 +316,13 @@ struct nfs4_label *nfs4_label_alloc(struct nfs_server *server, gfp_t flags)
        return label;
 }
 EXPORT_SYMBOL_GPL(nfs4_label_alloc);
+#else
+void inline nfs_setsecurity(struct inode *inode, struct nfs_fattr *fattr,
+                                       struct nfs4_label *label)
+{
+}
 #endif
+EXPORT_SYMBOL_GPL(nfs_setsecurity);
 
 /*
  * This is our front-end to iget that looks up inodes by file handle
@@ -412,6 +451,9 @@ nfs_fhget(struct super_block *sb, struct nfs_fh *fh, struct nfs_fattr *fattr, st
                         */
                        inode->i_blocks = nfs_calc_block_size(fattr->du.nfs3.used);
                }
+
+               nfs_setsecurity(inode, fattr, label);
+
                nfsi->attrtimeo = NFS_MINATTRTIMEO(inode);
                nfsi->attrtimeo_timestamp = now;
                nfsi->access_cache = RB_ROOT;
@@ -421,6 +463,7 @@ nfs_fhget(struct super_block *sb, struct nfs_fh *fh, struct nfs_fattr *fattr, st
                unlock_new_inode(inode);
        } else
                nfs_refresh_inode(inode, fattr);
+               nfs_setsecurity(inode, fattr, label);
        dprintk("NFS: nfs_fhget(%s/%Ld fh_crc=0x%08x ct=%d)\n",
                inode->i_sb->s_id,
                (long long)NFS_FILEID(inode),
@@ -477,7 +520,7 @@ nfs_setattr(struct dentry *dentry, struct iattr *attr)
                NFS_PROTO(inode)->return_delegation(inode);
        error = NFS_PROTO(inode)->setattr(dentry, fattr, attr);
        if (error == 0)
-               nfs_refresh_inode(inode, fattr);
+               error = nfs_refresh_inode(inode, fattr);
        nfs_free_fattr(fattr);
 out:
        return error;
@@ -741,16 +784,23 @@ EXPORT_SYMBOL_GPL(put_nfs_open_context);
  * Ensure that mmap has a recent RPC credential for use when writing out
  * shared pages
  */
-void nfs_file_set_open_context(struct file *filp, struct nfs_open_context *ctx)
+void nfs_inode_attach_open_context(struct nfs_open_context *ctx)
 {
-       struct inode *inode = file_inode(filp);
+       struct inode *inode = ctx->dentry->d_inode;
        struct nfs_inode *nfsi = NFS_I(inode);
 
-       filp->private_data = get_nfs_open_context(ctx);
        spin_lock(&inode->i_lock);
        list_add(&ctx->list, &nfsi->open_files);
        spin_unlock(&inode->i_lock);
 }
+EXPORT_SYMBOL_GPL(nfs_inode_attach_open_context);
+
+void nfs_file_set_open_context(struct file *filp, struct nfs_open_context *ctx)
+{
+       filp->private_data = get_nfs_open_context(ctx);
+       if (list_empty(&ctx->list))
+               nfs_inode_attach_open_context(ctx);
+}
 EXPORT_SYMBOL_GPL(nfs_file_set_open_context);
 
 /*
@@ -776,10 +826,11 @@ struct nfs_open_context *nfs_find_open_context(struct inode *inode, struct rpc_c
 
 static void nfs_file_clear_open_context(struct file *filp)
 {
-       struct inode *inode = file_inode(filp);
        struct nfs_open_context *ctx = nfs_file_open_context(filp);
 
        if (ctx) {
+               struct inode *inode = ctx->dentry->d_inode;
+
                filp->private_data = NULL;
                spin_lock(&inode->i_lock);
                list_move_tail(&ctx->list, &NFS_I(inode)->open_files);
@@ -885,7 +936,7 @@ int nfs_attribute_timeout(struct inode *inode)
        return !time_in_range_open(jiffies, nfsi->read_cache_jiffies, nfsi->read_cache_jiffies + nfsi->attrtimeo);
 }
 
-static int nfs_attribute_cache_expired(struct inode *inode)
+int nfs_attribute_cache_expired(struct inode *inode)
 {
        if (nfs_have_delegated_attributes(inode))
                return 0;
@@ -901,7 +952,8 @@ static int nfs_attribute_cache_expired(struct inode *inode)
  */
 int nfs_revalidate_inode(struct nfs_server *server, struct inode *inode)
 {
-       if (!(NFS_I(inode)->cache_validity & NFS_INO_INVALID_ATTR)
+       if (!(NFS_I(inode)->cache_validity &
+                       (NFS_INO_INVALID_ATTR|NFS_INO_INVALID_LABEL))
                        && !nfs_attribute_cache_expired(inode))
                return NFS_STALE(inode) ? -ESTALE : 0;
        return __nfs_revalidate_inode(server, inode);
@@ -1281,6 +1333,7 @@ int nfs_post_op_update_inode(struct inode *inode, struct nfs_fattr *fattr)
        spin_lock(&inode->i_lock);
        status = nfs_post_op_update_inode_locked(inode, fattr);
        spin_unlock(&inode->i_lock);
+
        return status;
 }
 EXPORT_SYMBOL_GPL(nfs_post_op_update_inode);
@@ -1521,7 +1574,7 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr)
                inode->i_blocks = fattr->du.nfs2.blocks;
 
        /* Update attrtimeo value if we're out of the unstable period */
-       if (invalid & NFS_INO_INVALID_ATTR) {
+       if (invalid & (NFS_INO_INVALID_ATTR|NFS_INO_INVALID_LABEL)) {
                nfs_inc_stats(inode, NFSIOS_ATTRINVALIDATE);
                nfsi->attrtimeo = NFS_MINATTRTIMEO(inode);
                nfsi->attrtimeo_timestamp = now;
@@ -1534,6 +1587,7 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr)
                }
        }
        invalid &= ~NFS_INO_INVALID_ATTR;
+       invalid &= ~NFS_INO_INVALID_LABEL;
        /* Don't invalidate the data if we were to blame */
        if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode)
                                || S_ISLNK(inode->i_mode)))
@@ -1676,12 +1730,11 @@ EXPORT_SYMBOL_GPL(nfs_net_id);
 static int nfs_net_init(struct net *net)
 {
        nfs_clients_init(net);
-       return nfs_dns_resolver_cache_init(net);
+       return 0;
 }
 
 static void nfs_net_exit(struct net *net)
 {
-       nfs_dns_resolver_cache_destroy(net);
        nfs_cleanup_cb_ident_idr(net);
 }
 
@@ -1699,10 +1752,6 @@ static int __init init_nfs_fs(void)
 {
        int err;
 
-       err = nfs_dns_resolver_init();
-       if (err < 0)
-               goto out10;;
-
        err = register_pernet_subsys(&nfs_net_ops);
        if (err < 0)
                goto out9;
@@ -1768,8 +1817,6 @@ out7:
 out8:
        unregister_pernet_subsys(&nfs_net_ops);
 out9:
-       nfs_dns_resolver_destroy();
-out10:
        return err;
 }
 
@@ -1782,7 +1829,6 @@ static void __exit exit_nfs_fs(void)
        nfs_destroy_nfspagecache();
        nfs_fscache_unregister();
        unregister_pernet_subsys(&nfs_net_ops);
-       nfs_dns_resolver_destroy();
 #ifdef CONFIG_PROC_FS
        rpc_proc_unregister(&init_net, "nfs");
 #endif