diff options
Diffstat (limited to 'fs/nfs/dir.c')
| -rw-r--r-- | fs/nfs/dir.c | 28 |
1 files changed, 19 insertions, 9 deletions
diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c index b38a57e78a63..2df639f143e8 100644 --- a/fs/nfs/dir.c +++ b/fs/nfs/dir.c | |||
| @@ -182,14 +182,16 @@ int nfs_readdir_filler(nfs_readdir_descriptor_t *desc, struct page *page) | |||
| 182 | /* We requested READDIRPLUS, but the server doesn't grok it */ | 182 | /* We requested READDIRPLUS, but the server doesn't grok it */ |
| 183 | if (error == -ENOTSUPP && desc->plus) { | 183 | if (error == -ENOTSUPP && desc->plus) { |
| 184 | NFS_SERVER(inode)->caps &= ~NFS_CAP_READDIRPLUS; | 184 | NFS_SERVER(inode)->caps &= ~NFS_CAP_READDIRPLUS; |
| 185 | NFS_FLAGS(inode) &= ~NFS_INO_ADVISE_RDPLUS; | 185 | clear_bit(NFS_INO_ADVISE_RDPLUS, &NFS_FLAGS(inode)); |
| 186 | desc->plus = 0; | 186 | desc->plus = 0; |
| 187 | goto again; | 187 | goto again; |
| 188 | } | 188 | } |
| 189 | goto error; | 189 | goto error; |
| 190 | } | 190 | } |
| 191 | SetPageUptodate(page); | 191 | SetPageUptodate(page); |
| 192 | NFS_FLAGS(inode) |= NFS_INO_INVALID_ATIME; | 192 | spin_lock(&inode->i_lock); |
| 193 | NFS_I(inode)->cache_validity |= NFS_INO_INVALID_ATIME; | ||
| 194 | spin_unlock(&inode->i_lock); | ||
| 193 | /* Ensure consistent page alignment of the data. | 195 | /* Ensure consistent page alignment of the data. |
| 194 | * Note: assumes we have exclusive access to this mapping either | 196 | * Note: assumes we have exclusive access to this mapping either |
| 195 | * through inode->i_sem or some other mechanism. | 197 | * through inode->i_sem or some other mechanism. |
| @@ -462,7 +464,9 @@ int uncached_readdir(nfs_readdir_descriptor_t *desc, void *dirent, | |||
| 462 | page, | 464 | page, |
| 463 | NFS_SERVER(inode)->dtsize, | 465 | NFS_SERVER(inode)->dtsize, |
| 464 | desc->plus); | 466 | desc->plus); |
| 465 | NFS_FLAGS(inode) |= NFS_INO_INVALID_ATIME; | 467 | spin_lock(&inode->i_lock); |
| 468 | NFS_I(inode)->cache_validity |= NFS_INO_INVALID_ATIME; | ||
| 469 | spin_unlock(&inode->i_lock); | ||
| 466 | desc->page = page; | 470 | desc->page = page; |
| 467 | desc->ptr = kmap(page); /* matching kunmap in nfs_do_filldir */ | 471 | desc->ptr = kmap(page); /* matching kunmap in nfs_do_filldir */ |
| 468 | if (desc->error >= 0) { | 472 | if (desc->error >= 0) { |
| @@ -545,7 +549,7 @@ static int nfs_readdir(struct file *filp, void *dirent, filldir_t filldir) | |||
| 545 | break; | 549 | break; |
| 546 | } | 550 | } |
| 547 | if (res == -ETOOSMALL && desc->plus) { | 551 | if (res == -ETOOSMALL && desc->plus) { |
| 548 | NFS_FLAGS(inode) &= ~NFS_INO_ADVISE_RDPLUS; | 552 | clear_bit(NFS_INO_ADVISE_RDPLUS, &NFS_FLAGS(inode)); |
| 549 | nfs_zap_caches(inode); | 553 | nfs_zap_caches(inode); |
| 550 | desc->plus = 0; | 554 | desc->plus = 0; |
| 551 | desc->entry->eof = 0; | 555 | desc->entry->eof = 0; |
| @@ -608,7 +612,7 @@ static inline int nfs_check_verifier(struct inode *dir, struct dentry *dentry) | |||
| 608 | { | 612 | { |
| 609 | if (IS_ROOT(dentry)) | 613 | if (IS_ROOT(dentry)) |
| 610 | return 1; | 614 | return 1; |
| 611 | if ((NFS_FLAGS(dir) & NFS_INO_INVALID_ATTR) != 0 | 615 | if ((NFS_I(dir)->cache_validity & NFS_INO_INVALID_ATTR) != 0 |
| 612 | || nfs_attribute_timeout(dir)) | 616 | || nfs_attribute_timeout(dir)) |
| 613 | return 0; | 617 | return 0; |
| 614 | return nfs_verify_change_attribute(dir, (unsigned long)dentry->d_fsdata); | 618 | return nfs_verify_change_attribute(dir, (unsigned long)dentry->d_fsdata); |
| @@ -935,6 +939,7 @@ static struct dentry *nfs_atomic_lookup(struct inode *dir, struct dentry *dentry | |||
| 935 | error = nfs_revalidate_inode(NFS_SERVER(dir), dir); | 939 | error = nfs_revalidate_inode(NFS_SERVER(dir), dir); |
| 936 | if (error < 0) { | 940 | if (error < 0) { |
| 937 | res = ERR_PTR(error); | 941 | res = ERR_PTR(error); |
| 942 | unlock_kernel(); | ||
| 938 | goto out; | 943 | goto out; |
| 939 | } | 944 | } |
| 940 | 945 | ||
| @@ -1575,11 +1580,12 @@ out: | |||
| 1575 | 1580 | ||
| 1576 | int nfs_access_get_cached(struct inode *inode, struct rpc_cred *cred, struct nfs_access_entry *res) | 1581 | int nfs_access_get_cached(struct inode *inode, struct rpc_cred *cred, struct nfs_access_entry *res) |
| 1577 | { | 1582 | { |
| 1578 | struct nfs_access_entry *cache = &NFS_I(inode)->cache_access; | 1583 | struct nfs_inode *nfsi = NFS_I(inode); |
| 1584 | struct nfs_access_entry *cache = &nfsi->cache_access; | ||
| 1579 | 1585 | ||
| 1580 | if (cache->cred != cred | 1586 | if (cache->cred != cred |
| 1581 | || time_after(jiffies, cache->jiffies + NFS_ATTRTIMEO(inode)) | 1587 | || time_after(jiffies, cache->jiffies + NFS_ATTRTIMEO(inode)) |
| 1582 | || (NFS_FLAGS(inode) & NFS_INO_INVALID_ACCESS)) | 1588 | || (nfsi->cache_validity & NFS_INO_INVALID_ACCESS)) |
| 1583 | return -ENOENT; | 1589 | return -ENOENT; |
| 1584 | memcpy(res, cache, sizeof(*res)); | 1590 | memcpy(res, cache, sizeof(*res)); |
| 1585 | return 0; | 1591 | return 0; |
| @@ -1587,14 +1593,18 @@ int nfs_access_get_cached(struct inode *inode, struct rpc_cred *cred, struct nfs | |||
| 1587 | 1593 | ||
| 1588 | void nfs_access_add_cache(struct inode *inode, struct nfs_access_entry *set) | 1594 | void nfs_access_add_cache(struct inode *inode, struct nfs_access_entry *set) |
| 1589 | { | 1595 | { |
| 1590 | struct nfs_access_entry *cache = &NFS_I(inode)->cache_access; | 1596 | struct nfs_inode *nfsi = NFS_I(inode); |
| 1597 | struct nfs_access_entry *cache = &nfsi->cache_access; | ||
| 1591 | 1598 | ||
| 1592 | if (cache->cred != set->cred) { | 1599 | if (cache->cred != set->cred) { |
| 1593 | if (cache->cred) | 1600 | if (cache->cred) |
| 1594 | put_rpccred(cache->cred); | 1601 | put_rpccred(cache->cred); |
| 1595 | cache->cred = get_rpccred(set->cred); | 1602 | cache->cred = get_rpccred(set->cred); |
| 1596 | } | 1603 | } |
| 1597 | NFS_FLAGS(inode) &= ~NFS_INO_INVALID_ACCESS; | 1604 | /* FIXME: replace current access_cache BKL reliance with inode->i_lock */ |
| 1605 | spin_lock(&inode->i_lock); | ||
| 1606 | nfsi->cache_validity &= ~NFS_INO_INVALID_ACCESS; | ||
| 1607 | spin_unlock(&inode->i_lock); | ||
| 1598 | cache->jiffies = set->jiffies; | 1608 | cache->jiffies = set->jiffies; |
| 1599 | cache->mask = set->mask; | 1609 | cache->mask = set->mask; |
| 1600 | } | 1610 | } |
