diff options
Diffstat (limited to 'fs/nfs/inode.c')
-rw-r--r-- | fs/nfs/inode.c | 34 |
1 files changed, 23 insertions, 11 deletions
diff --git a/fs/nfs/inode.c b/fs/nfs/inode.c index f68c22215b14..966a8850aa30 100644 --- a/fs/nfs/inode.c +++ b/fs/nfs/inode.c | |||
@@ -192,7 +192,7 @@ void nfs_invalidate_atime(struct inode *inode) | |||
192 | */ | 192 | */ |
193 | static void nfs_invalidate_inode(struct inode *inode) | 193 | static void nfs_invalidate_inode(struct inode *inode) |
194 | { | 194 | { |
195 | set_bit(NFS_INO_STALE, &NFS_FLAGS(inode)); | 195 | set_bit(NFS_INO_STALE, &NFS_I(inode)->flags); |
196 | nfs_zap_caches_locked(inode); | 196 | nfs_zap_caches_locked(inode); |
197 | } | 197 | } |
198 | 198 | ||
@@ -229,7 +229,7 @@ nfs_init_locked(struct inode *inode, void *opaque) | |||
229 | struct nfs_find_desc *desc = (struct nfs_find_desc *)opaque; | 229 | struct nfs_find_desc *desc = (struct nfs_find_desc *)opaque; |
230 | struct nfs_fattr *fattr = desc->fattr; | 230 | struct nfs_fattr *fattr = desc->fattr; |
231 | 231 | ||
232 | NFS_FILEID(inode) = fattr->fileid; | 232 | set_nfs_fileid(inode, fattr->fileid); |
233 | nfs_copy_fh(NFS_FH(inode), desc->fh); | 233 | nfs_copy_fh(NFS_FH(inode), desc->fh); |
234 | return 0; | 234 | return 0; |
235 | } | 235 | } |
@@ -291,7 +291,7 @@ nfs_fhget(struct super_block *sb, struct nfs_fh *fh, struct nfs_fattr *fattr) | |||
291 | inode->i_fop = &nfs_dir_operations; | 291 | inode->i_fop = &nfs_dir_operations; |
292 | if (nfs_server_capable(inode, NFS_CAP_READDIRPLUS) | 292 | if (nfs_server_capable(inode, NFS_CAP_READDIRPLUS) |
293 | && fattr->size <= NFS_LIMIT_READDIRPLUS) | 293 | && fattr->size <= NFS_LIMIT_READDIRPLUS) |
294 | set_bit(NFS_INO_ADVISE_RDPLUS, &NFS_FLAGS(inode)); | 294 | set_bit(NFS_INO_ADVISE_RDPLUS, &NFS_I(inode)->flags); |
295 | /* Deal with crossing mountpoints */ | 295 | /* Deal with crossing mountpoints */ |
296 | if (!nfs_fsid_equal(&NFS_SB(sb)->fsid, &fattr->fsid)) { | 296 | if (!nfs_fsid_equal(&NFS_SB(sb)->fsid, &fattr->fsid)) { |
297 | if (fattr->valid & NFS_ATTR_FATTR_V4_REFERRAL) | 297 | if (fattr->valid & NFS_ATTR_FATTR_V4_REFERRAL) |
@@ -457,9 +457,18 @@ int nfs_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat) | |||
457 | int need_atime = NFS_I(inode)->cache_validity & NFS_INO_INVALID_ATIME; | 457 | int need_atime = NFS_I(inode)->cache_validity & NFS_INO_INVALID_ATIME; |
458 | int err; | 458 | int err; |
459 | 459 | ||
460 | /* Flush out writes to the server in order to update c/mtime */ | 460 | /* |
461 | if (S_ISREG(inode->i_mode)) | 461 | * Flush out writes to the server in order to update c/mtime. |
462 | * | ||
463 | * Hold the i_mutex to suspend application writes temporarily; | ||
464 | * this prevents long-running writing applications from blocking | ||
465 | * nfs_wb_nocommit. | ||
466 | */ | ||
467 | if (S_ISREG(inode->i_mode)) { | ||
468 | mutex_lock(&inode->i_mutex); | ||
462 | nfs_wb_nocommit(inode); | 469 | nfs_wb_nocommit(inode); |
470 | mutex_unlock(&inode->i_mutex); | ||
471 | } | ||
463 | 472 | ||
464 | /* | 473 | /* |
465 | * We may force a getattr if the user cares about atime. | 474 | * We may force a getattr if the user cares about atime. |
@@ -655,7 +664,7 @@ __nfs_revalidate_inode(struct nfs_server *server, struct inode *inode) | |||
655 | if (status == -ESTALE) { | 664 | if (status == -ESTALE) { |
656 | nfs_zap_caches(inode); | 665 | nfs_zap_caches(inode); |
657 | if (!S_ISDIR(inode->i_mode)) | 666 | if (!S_ISDIR(inode->i_mode)) |
658 | set_bit(NFS_INO_STALE, &NFS_FLAGS(inode)); | 667 | set_bit(NFS_INO_STALE, &NFS_I(inode)->flags); |
659 | } | 668 | } |
660 | goto out; | 669 | goto out; |
661 | } | 670 | } |
@@ -810,8 +819,9 @@ static void nfs_wcc_update_inode(struct inode *inode, struct nfs_fattr *fattr) | |||
810 | if (S_ISDIR(inode->i_mode)) | 819 | if (S_ISDIR(inode->i_mode)) |
811 | nfsi->cache_validity |= NFS_INO_INVALID_DATA; | 820 | nfsi->cache_validity |= NFS_INO_INVALID_DATA; |
812 | } | 821 | } |
813 | if (inode->i_size == fattr->pre_size && nfsi->npages == 0) | 822 | if (inode->i_size == nfs_size_to_loff_t(fattr->pre_size) && |
814 | inode->i_size = fattr->size; | 823 | nfsi->npages == 0) |
824 | inode->i_size = nfs_size_to_loff_t(fattr->size); | ||
815 | } | 825 | } |
816 | } | 826 | } |
817 | 827 | ||
@@ -1015,7 +1025,8 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr) | |||
1015 | dprintk("NFS: mtime change on server for file %s/%ld\n", | 1025 | dprintk("NFS: mtime change on server for file %s/%ld\n", |
1016 | inode->i_sb->s_id, inode->i_ino); | 1026 | inode->i_sb->s_id, inode->i_ino); |
1017 | invalid |= NFS_INO_INVALID_ATTR|NFS_INO_INVALID_DATA; | 1027 | invalid |= NFS_INO_INVALID_ATTR|NFS_INO_INVALID_DATA; |
1018 | nfsi->cache_change_attribute = now; | 1028 | if (S_ISDIR(inode->i_mode)) |
1029 | nfs_force_lookup_revalidate(inode); | ||
1019 | } | 1030 | } |
1020 | /* If ctime has changed we should definitely clear access+acl caches */ | 1031 | /* If ctime has changed we should definitely clear access+acl caches */ |
1021 | if (!timespec_equal(&inode->i_ctime, &fattr->ctime)) | 1032 | if (!timespec_equal(&inode->i_ctime, &fattr->ctime)) |
@@ -1024,7 +1035,8 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr) | |||
1024 | dprintk("NFS: change_attr change on server for file %s/%ld\n", | 1035 | dprintk("NFS: change_attr change on server for file %s/%ld\n", |
1025 | inode->i_sb->s_id, inode->i_ino); | 1036 | inode->i_sb->s_id, inode->i_ino); |
1026 | invalid |= NFS_INO_INVALID_ATTR|NFS_INO_INVALID_DATA|NFS_INO_INVALID_ACCESS|NFS_INO_INVALID_ACL; | 1037 | invalid |= NFS_INO_INVALID_ATTR|NFS_INO_INVALID_DATA|NFS_INO_INVALID_ACCESS|NFS_INO_INVALID_ACL; |
1027 | nfsi->cache_change_attribute = now; | 1038 | if (S_ISDIR(inode->i_mode)) |
1039 | nfs_force_lookup_revalidate(inode); | ||
1028 | } | 1040 | } |
1029 | 1041 | ||
1030 | /* Check if our cached file size is stale */ | 1042 | /* Check if our cached file size is stale */ |
@@ -1129,7 +1141,7 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr) | |||
1129 | void nfs4_clear_inode(struct inode *inode) | 1141 | void nfs4_clear_inode(struct inode *inode) |
1130 | { | 1142 | { |
1131 | /* If we are holding a delegation, return it! */ | 1143 | /* If we are holding a delegation, return it! */ |
1132 | nfs_inode_return_delegation(inode); | 1144 | nfs_inode_return_delegation_noreclaim(inode); |
1133 | /* First call standard NFS clear_inode() code */ | 1145 | /* First call standard NFS clear_inode() code */ |
1134 | nfs_clear_inode(inode); | 1146 | nfs_clear_inode(inode); |
1135 | } | 1147 | } |