Skip to content

Commit

Permalink
---
Browse files Browse the repository at this point in the history
yaml
---
r: 139522
b: refs/heads/master
c: 72cb77f
h: refs/heads/master
v: v3
  • Loading branch information
Trond Myklebust authored and Trond Myklebust committed Mar 11, 2009
1 parent d03cca2 commit b135cff
Show file tree
Hide file tree
Showing 8 changed files with 44 additions and 30 deletions.
2 changes: 1 addition & 1 deletion [refs]
Original file line number Diff line number Diff line change
@@ -1,2 +1,2 @@
---
refs/heads/master: fb8a1f11b64e213d94dfa1cebb2a42a7b8c115c4
refs/heads/master: 72cb77f4a5ace37b12dcb47a0e8637a2c28ad881
9 changes: 9 additions & 0 deletions trunk/fs/nfs/file.c
Original file line number Diff line number Diff line change
Expand Up @@ -354,6 +354,15 @@ static int nfs_write_begin(struct file *file, struct address_space *mapping,
file->f_path.dentry->d_name.name,
mapping->host->i_ino, len, (long long) pos);

/*
* Prevent starvation issues if someone is doing a consistency
* sync-to-disk
*/
ret = wait_on_bit(&NFS_I(mapping->host)->flags, NFS_INO_FLUSHING,
nfs_wait_bit_killable, TASK_KILLABLE);
if (ret)
return ret;

page = grab_cache_page_write_begin(mapping, index, flags);
if (!page)
return -ENOMEM;
Expand Down
12 changes: 12 additions & 0 deletions trunk/fs/nfs/inode.c
Original file line number Diff line number Diff line change
Expand Up @@ -65,6 +65,18 @@ nfs_fattr_to_ino_t(struct nfs_fattr *fattr)
return nfs_fileid_to_ino_t(fattr->fileid);
}

/**
* nfs_wait_bit_killable - helper for functions that are sleeping on bit locks
* @word: long word containing the bit lock
*/
int nfs_wait_bit_killable(void *word)
{
if (fatal_signal_pending(current))
return -ERESTARTSYS;
schedule();
return 0;
}

/**
* nfs_compat_user_ino64 - returns the user-visible inode number
* @fileid: 64-bit fileid
Expand Down
1 change: 1 addition & 0 deletions trunk/fs/nfs/internal.h
Original file line number Diff line number Diff line change
Expand Up @@ -165,6 +165,7 @@ extern void nfs_clear_inode(struct inode *);
extern void nfs4_clear_inode(struct inode *);
#endif
void nfs_zap_acl_cache(struct inode *inode);
extern int nfs_wait_bit_killable(void *word);

/* super.c */
void nfs_parse_ip_address(char *, size_t, struct sockaddr *, size_t *);
Expand Down
10 changes: 1 addition & 9 deletions trunk/fs/nfs/nfs4proc.c
Original file line number Diff line number Diff line change
Expand Up @@ -193,22 +193,14 @@ static void nfs4_setup_readdir(u64 cookie, __be32 *verifier, struct dentry *dent
kunmap_atomic(start, KM_USER0);
}

static int nfs4_wait_bit_killable(void *word)
{
if (fatal_signal_pending(current))
return -ERESTARTSYS;
schedule();
return 0;
}

static int nfs4_wait_clnt_recover(struct nfs_client *clp)
{
int res;

might_sleep();

res = wait_on_bit(&clp->cl_state, NFS4CLNT_MANAGER_RUNNING,
nfs4_wait_bit_killable, TASK_KILLABLE);
nfs_wait_bit_killable, TASK_KILLABLE);
return res;
}

Expand Down
11 changes: 0 additions & 11 deletions trunk/fs/nfs/pagelist.c
Original file line number Diff line number Diff line change
Expand Up @@ -176,17 +176,6 @@ void nfs_release_request(struct nfs_page *req)
kref_put(&req->wb_kref, nfs_free_request);
}

static int nfs_wait_bit_killable(void *word)
{
int ret = 0;

if (fatal_signal_pending(current))
ret = -ERESTARTSYS;
else
schedule();
return ret;
}

/**
* nfs_wait_on_request - Wait for a request to complete.
* @req: request to wait upon.
Expand Down
28 changes: 19 additions & 9 deletions trunk/fs/nfs/write.c
Original file line number Diff line number Diff line change
Expand Up @@ -313,19 +313,34 @@ static int nfs_writepages_callback(struct page *page, struct writeback_control *
int nfs_writepages(struct address_space *mapping, struct writeback_control *wbc)
{
struct inode *inode = mapping->host;
unsigned long *bitlock = &NFS_I(inode)->flags;
struct nfs_pageio_descriptor pgio;
int err;

/* Stop dirtying of new pages while we sync */
err = wait_on_bit_lock(bitlock, NFS_INO_FLUSHING,
nfs_wait_bit_killable, TASK_KILLABLE);
if (err)
goto out_err;

nfs_inc_stats(inode, NFSIOS_VFSWRITEPAGES);

nfs_pageio_init_write(&pgio, inode, wb_priority(wbc));
err = write_cache_pages(mapping, wbc, nfs_writepages_callback, &pgio);
nfs_pageio_complete(&pgio);

clear_bit_unlock(NFS_INO_FLUSHING, bitlock);
smp_mb__after_clear_bit();
wake_up_bit(bitlock, NFS_INO_FLUSHING);

if (err < 0)
return err;
if (pgio.pg_error < 0)
return pgio.pg_error;
goto out_err;
err = pgio.pg_error;
if (err < 0)
goto out_err;
return 0;
out_err:
return err;
}

/*
Expand Down Expand Up @@ -1432,18 +1447,13 @@ static int nfs_write_mapping(struct address_space *mapping, int how)
{
struct writeback_control wbc = {
.bdi = mapping->backing_dev_info,
.sync_mode = WB_SYNC_NONE,
.sync_mode = WB_SYNC_ALL,
.nr_to_write = LONG_MAX,
.range_start = 0,
.range_end = LLONG_MAX,
.for_writepages = 1,
};
int ret;

ret = __nfs_write_mapping(mapping, &wbc, how);
if (ret < 0)
return ret;
wbc.sync_mode = WB_SYNC_ALL;
return __nfs_write_mapping(mapping, &wbc, how);
}

Expand Down
1 change: 1 addition & 0 deletions trunk/include/linux/nfs_fs.h
Original file line number Diff line number Diff line change
Expand Up @@ -206,6 +206,7 @@ struct nfs_inode {
#define NFS_INO_STALE (1) /* possible stale inode */
#define NFS_INO_ACL_LRU_SET (2) /* Inode is on the LRU list */
#define NFS_INO_MOUNTPOINT (3) /* inode is remote mountpoint */
#define NFS_INO_FLUSHING (4) /* inode is flushing out data */

static inline struct nfs_inode *NFS_I(const struct inode *inode)
{
Expand Down

0 comments on commit b135cff

Please sign in to comment.