This source file includes following definitions.
- do_read_nfs_sync
- nfs_read_cb
- do_read_nfs_async
- nfs_readpage
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21 #include <linux/sched.h>
22 #include <linux/kernel.h>
23 #include <linux/errno.h>
24 #include <linux/fcntl.h>
25 #include <linux/stat.h>
26 #include <linux/mm.h>
27 #include <linux/nfs_fs.h>
28 #include <linux/nfsiod.h>
29 #include <linux/malloc.h>
30 #include <linux/pagemap.h>
31
32 #include <asm/segment.h>
33 #include <asm/system.h>
34
35 #undef DEBUG_BIO
36 #ifdef DEBUG_BIO
37 #define dprintk(args...) printk(## args)
38 #else
39 #define dprintk(args...)
40 #endif
41
42 static inline int
43 do_read_nfs_sync(struct inode * inode, struct page * page)
44 {
45 struct nfs_fattr fattr;
46 int result, refresh = 0;
47 int count = PAGE_SIZE;
48 int rsize = NFS_SERVER(inode)->rsize;
49 char *buf = (char *) page_address(page);
50 unsigned long pos = page->offset;
51
52 dprintk("NFS: do_read_nfs_sync(%p)\n", page);
53
54 set_bit(PG_locked, &page->flags);
55 clear_bit(PG_error, &page->flags);
56
57 do {
58 if (count < rsize)
59 rsize = count;
60 result = nfs_proc_read(NFS_SERVER(inode), NFS_FH(inode),
61 pos, rsize, buf, &fattr);
62 dprintk("nfs_proc_read(%s, (%x,%lx), %ld, %d, %p) = %d\n",
63 NFS_SERVER(inode)->hostname,
64 inode->i_dev, inode->i_ino,
65 pos, rsize, buf, result);
66 if (result < 0)
67 break;
68 refresh = 1;
69 count -= result;
70 pos += result;
71 buf += result;
72 if (result < rsize)
73 break;
74 } while (count);
75
76 memset(buf, 0, count);
77 if (refresh) {
78 nfs_refresh_inode(inode, &fattr);
79 result = 0;
80 set_bit(PG_uptodate, &page->flags);
81 }
82 clear_bit(PG_locked, &page->flags);
83 wake_up(&page->wait);
84 return result;
85 }
86
87
88
89
90
91 static void
92 nfs_read_cb(int result, struct nfsiod_req *req)
93 {
94 struct page *page = (struct page *) req->rq_cdata;
95 static int succ = 0, fail = 0;
96
97 dprintk("BIO: received callback for page %p, result %d\n",
98 page, result);
99
100 if (result >= 0
101 && (result = nfs_proc_read_reply(&req->rq_rpcreq)) >= 0) {
102 succ++;
103 set_bit(PG_uptodate, &page->flags);
104 } else {
105 fail++;
106 printk("BIO: %d successful reads, %d failures\n", succ, fail);
107 set_bit(PG_error, &page->flags);
108 }
109 clear_bit(PG_locked, &page->flags);
110 wake_up(&page->wait);
111 free_page(page_address(page));
112 }
113
114 static inline int
115 do_read_nfs_async(struct inode *inode, struct page *page)
116 {
117 struct nfsiod_req *req;
118 int result = -1;
119
120 dprintk("NFS: do_read_nfs_async(%p)\n", page);
121
122 set_bit(PG_locked, &page->flags);
123 clear_bit(PG_error, &page->flags);
124
125 if (!(req = nfsiod_reserve(NFS_SERVER(inode), nfs_read_cb)))
126 goto done;
127 result = nfs_proc_read_request(&req->rq_rpcreq,
128 NFS_SERVER(inode), NFS_FH(inode),
129 page->offset, PAGE_SIZE,
130 (__u32 *) page_address(page));
131 if (result >= 0) {
132 req->rq_cdata = page;
133 page->count++;
134 result = nfsiod_enqueue(req);
135 if (result >= 0)
136 dprintk("NFS: enqueued async READ request.\n");
137 }
138 if (result < 0) {
139 dprintk("NFS: deferring async READ request.\n");
140 nfsiod_release(req);
141 clear_bit(PG_locked, &page->flags);
142 wake_up(&page->wait);
143 }
144
145 done:
146 return result < 0? result : 0;
147 }
148
149 int
150 nfs_readpage(struct inode *inode, struct page *page)
151 {
152 unsigned long address;
153 int error = -1;
154
155 dprintk("NFS: nfs_readpage %08lx\n", page_address(page));
156 address = page_address(page);
157 page->count++;
158 if (!PageError(page) && NFS_SERVER(inode)->rsize >= PAGE_SIZE)
159 error = do_read_nfs_async(inode, page);
160 if (error < 0)
161 error = do_read_nfs_sync(inode, page);
162 free_page(address);
163 return error;
164 }