Commit 96c41455 authored by Trond Myklebust's avatar Trond Myklebust

NFS: Fix writepage(s) error handling to not report errors twice

If writepage()/writepages() saw an error, but handled it without
reporting it, we should not be re-reporting that error on exit.
Signed-off-by: default avatarTrond Myklebust <trond.myklebust@hammerspace.com>
parent 8f54c7a4
...@@ -621,12 +621,12 @@ static int nfs_page_async_flush(struct nfs_pageio_descriptor *pgio, ...@@ -621,12 +621,12 @@ static int nfs_page_async_flush(struct nfs_pageio_descriptor *pgio,
WARN_ON_ONCE(test_bit(PG_CLEAN, &req->wb_flags)); WARN_ON_ONCE(test_bit(PG_CLEAN, &req->wb_flags));
/* If there is a fatal error that covers this write, just exit */ /* If there is a fatal error that covers this write, just exit */
ret = 0;
mapping = page_file_mapping(page); mapping = page_file_mapping(page);
if (test_bit(AS_ENOSPC, &mapping->flags) || ret = pgio->pg_error;
test_bit(AS_EIO, &mapping->flags)) if (nfs_error_is_fatal_on_server(ret))
goto out_launder; goto out_launder;
ret = 0;
if (!nfs_pageio_add_request(pgio, req)) { if (!nfs_pageio_add_request(pgio, req)) {
ret = pgio->pg_error; ret = pgio->pg_error;
/* /*
...@@ -638,6 +638,7 @@ static int nfs_page_async_flush(struct nfs_pageio_descriptor *pgio, ...@@ -638,6 +638,7 @@ static int nfs_page_async_flush(struct nfs_pageio_descriptor *pgio,
} else } else
ret = -EAGAIN; ret = -EAGAIN;
nfs_redirty_request(req); nfs_redirty_request(req);
pgio->pg_error = 0;
} else } else
nfs_add_stats(page_file_mapping(page)->host, nfs_add_stats(page_file_mapping(page)->host,
NFSIOS_WRITEPAGES, 1); NFSIOS_WRITEPAGES, 1);
...@@ -657,7 +658,7 @@ static int nfs_do_writepage(struct page *page, struct writeback_control *wbc, ...@@ -657,7 +658,7 @@ static int nfs_do_writepage(struct page *page, struct writeback_control *wbc,
ret = nfs_page_async_flush(pgio, page); ret = nfs_page_async_flush(pgio, page);
if (ret == -EAGAIN) { if (ret == -EAGAIN) {
redirty_page_for_writepage(wbc, page); redirty_page_for_writepage(wbc, page);
ret = 0; ret = AOP_WRITEPAGE_ACTIVATE;
} }
return ret; return ret;
} }
...@@ -676,10 +677,11 @@ static int nfs_writepage_locked(struct page *page, ...@@ -676,10 +677,11 @@ static int nfs_writepage_locked(struct page *page,
nfs_pageio_init_write(&pgio, inode, 0, nfs_pageio_init_write(&pgio, inode, 0,
false, &nfs_async_write_completion_ops); false, &nfs_async_write_completion_ops);
err = nfs_do_writepage(page, wbc, &pgio); err = nfs_do_writepage(page, wbc, &pgio);
pgio.pg_error = 0;
nfs_pageio_complete(&pgio); nfs_pageio_complete(&pgio);
if (err < 0) if (err < 0)
return err; return err;
if (pgio.pg_error < 0) if (nfs_error_is_fatal(pgio.pg_error))
return pgio.pg_error; return pgio.pg_error;
return 0; return 0;
} }
...@@ -689,7 +691,8 @@ int nfs_writepage(struct page *page, struct writeback_control *wbc) ...@@ -689,7 +691,8 @@ int nfs_writepage(struct page *page, struct writeback_control *wbc)
int ret; int ret;
ret = nfs_writepage_locked(page, wbc); ret = nfs_writepage_locked(page, wbc);
unlock_page(page); if (ret != AOP_WRITEPAGE_ACTIVATE)
unlock_page(page);
return ret; return ret;
} }
...@@ -698,7 +701,8 @@ static int nfs_writepages_callback(struct page *page, struct writeback_control * ...@@ -698,7 +701,8 @@ static int nfs_writepages_callback(struct page *page, struct writeback_control *
int ret; int ret;
ret = nfs_do_writepage(page, wbc, data); ret = nfs_do_writepage(page, wbc, data);
unlock_page(page); if (ret != AOP_WRITEPAGE_ACTIVATE)
unlock_page(page);
return ret; return ret;
} }
...@@ -724,13 +728,14 @@ int nfs_writepages(struct address_space *mapping, struct writeback_control *wbc) ...@@ -724,13 +728,14 @@ int nfs_writepages(struct address_space *mapping, struct writeback_control *wbc)
&nfs_async_write_completion_ops); &nfs_async_write_completion_ops);
pgio.pg_io_completion = ioc; pgio.pg_io_completion = ioc;
err = write_cache_pages(mapping, wbc, nfs_writepages_callback, &pgio); err = write_cache_pages(mapping, wbc, nfs_writepages_callback, &pgio);
pgio.pg_error = 0;
nfs_pageio_complete(&pgio); nfs_pageio_complete(&pgio);
nfs_io_completion_put(ioc); nfs_io_completion_put(ioc);
if (err < 0) if (err < 0)
goto out_err; goto out_err;
err = pgio.pg_error; err = pgio.pg_error;
if (err < 0) if (nfs_error_is_fatal(err))
goto out_err; goto out_err;
return 0; return 0;
out_err: out_err:
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment