[pnfs] [PATCH 09/10] pnfs: Enable O_DIRECT read path.
Dean Hildebrand
seattleplus at gmail.com
Tue Jul 8 17:54:05 EDT 2008
Signed-off-by: Dean Hildebrand <dhildeb at us.ibm.com>
---
fs/nfs/direct.c | 37 +++++++++++++++++++++++++++++++++++--
1 files changed, 35 insertions(+), 2 deletions(-)
diff --git a/fs/nfs/direct.c b/fs/nfs/direct.c
index 854ed47..a397a9c 100644
--- a/fs/nfs/direct.c
+++ b/fs/nfs/direct.c
@@ -55,6 +55,7 @@
#include "internal.h"
#include "iostat.h"
+#include "pnfs.h"
#define NFSDBG_FACILITY NFSDBG_VFS
@@ -189,12 +190,22 @@ static ssize_t nfs_direct_wait(struct nfs_direct_req *dreq)
{
ssize_t result = -EIOCBQUEUED;
+ if (!pnfs_use_rpc(NFS_SERVER(dreq->inode))) {
+ /* FIXME: Right now non-rpc layout types must perform
+ * syncronous direct i/o.
+ * New pNFS callback to wait on outstanding requests?
+ */
+ result = 0;
+ goto set_result;
+ }
+
/* Async requests don't wait here */
if (dreq->iocb)
goto out;
result = wait_for_completion_killable(&dreq->completion);
+set_result:
if (!result)
result = dreq->error;
if (!result)
@@ -329,6 +340,16 @@ static ssize_t nfs_direct_read_schedule_segment(struct nfs_direct_req *dreq,
unsigned int pgbase;
int result;
ssize_t started = 0;
+ size_t pnfs_stripe_rem = count;
+
+ /* pnfs_stripe_rem will be set to the remaining bytes in
+ * the first stripe_unit (which for standard nfs is count)
+ */
+ pnfs_direct_init_io(inode, ctx, count, pos, 0, &rsize,
+ &pnfs_stripe_rem);
+
+ dprintk("%s: pos %llu count %Zu wsize %Zu\n",
+ __func__, pos, count, rsize);
do {
struct nfs_read_data *data;
@@ -336,6 +357,10 @@ static ssize_t nfs_direct_read_schedule_segment(struct nfs_direct_req *dreq,
pgbase = user_addr & ~PAGE_MASK;
bytes = min(rsize,count);
+#if defined(CONFIG_PNFS)
+ bytes = min(bytes, pnfs_stripe_rem);
+ pnfs_stripe_rem = rsize;
+#endif /* CONFIG_PNFS */
result = -ENOMEM;
data = nfs_readdata_alloc(nfs_page_array_len(pgbase, bytes));
@@ -377,8 +402,16 @@ static ssize_t nfs_direct_read_schedule_segment(struct nfs_direct_req *dreq,
data->res.eof = 0;
data->res.count = bytes;
- if (nfs_direct_read_execute(data, &task_setup_data, &msg))
- break;
+ result = pnfs_try_to_read_data(data, &nfs_read_direct_ops);
+#if defined(CONFIG_PNFS)
+ if (result == PNFS_ATTEMPTED && data->pdata.pnfs_error) {
+ result = data->pdata.pnfs_error;
+ break;
+ }
+#endif /* CONFIG_PNFS */
+ if (result == PNFS_NOT_ATTEMPTED &&
+ nfs_direct_read_execute(data, &task_setup_data, &msg))
+ break;
started += bytes;
user_addr += bytes;
--
1.5.3.3
More information about the pNFS
mailing list