hc
2024-05-10 9999e48639b3cecb08ffb37358bcba3b48161b29
kernel/fs/nfs/pnfs.h
....@@ -66,6 +66,7 @@
6666 struct pnfs_layout_segment {
6767 struct list_head pls_list;
6868 struct list_head pls_lc_list;
69
+ struct list_head pls_commits;
6970 struct pnfs_layout_range pls_range;
7071 refcount_t pls_refcount;
7172 u32 pls_seq;
....@@ -79,6 +80,10 @@
7980 PNFS_TRY_AGAIN = 2,
8081 };
8182
83
+/* error codes for internal use */
84
+#define NFS4ERR_RESET_TO_MDS 12001
85
+#define NFS4ERR_RESET_TO_PNFS 12002
86
+
8287 #ifdef CONFIG_NFS_V4_1
8388
8489 #define LAYOUT_NFSV4_1_MODULE_PREFIX "nfs-layouttype4"
....@@ -91,10 +96,6 @@
9196 #define NFS4_DEF_DS_RETRANS 5
9297 #define PNFS_DEVICE_RETRY_TIMEOUT (120*HZ)
9398
94
-/* error codes for internal use */
95
-#define NFS4ERR_RESET_TO_MDS 12001
96
-#define NFS4ERR_RESET_TO_PNFS 12002
97
-
9899 enum {
99100 NFS_LAYOUT_RO_FAILED = 0, /* get ro layout failed stop trying */
100101 NFS_LAYOUT_RW_FAILED, /* get rw layout failed stop trying */
....@@ -105,6 +106,8 @@
105106 NFS_LAYOUT_INVALID_STID, /* layout stateid id is invalid */
106107 NFS_LAYOUT_FIRST_LAYOUTGET, /* Serialize first layoutget */
107108 NFS_LAYOUT_INODE_FREEING, /* The inode is being freed */
109
+ NFS_LAYOUT_HASHED, /* The layout visible */
110
+ NFS_LAYOUT_DRAIN,
108111 };
109112
110113 enum layoutdriver_policy_flags {
....@@ -126,6 +129,7 @@
126129 struct module *owner;
127130 unsigned flags;
128131 unsigned max_deviceinfo_size;
132
+ unsigned max_layoutget_response;
129133
130134 int (*set_layoutdriver) (struct nfs_server *, const struct nfs_fh *);
131135 int (*clear_layoutdriver) (struct nfs_server *);
....@@ -147,22 +151,6 @@
147151 const struct nfs_pageio_ops *pg_write_ops;
148152
149153 struct pnfs_ds_commit_info *(*get_ds_info) (struct inode *inode);
150
- void (*mark_request_commit) (struct nfs_page *req,
151
- struct pnfs_layout_segment *lseg,
152
- struct nfs_commit_info *cinfo,
153
- u32 ds_commit_idx);
154
- void (*clear_request_commit) (struct nfs_page *req,
155
- struct nfs_commit_info *cinfo);
156
- int (*scan_commit_lists) (struct nfs_commit_info *cinfo,
157
- int max);
158
- void (*recover_commit_reqs) (struct list_head *list,
159
- struct nfs_commit_info *cinfo);
160
- struct nfs_page * (*search_commit_reqs)(struct nfs_commit_info *cinfo,
161
- struct page *page);
162
- int (*commit_pagelist)(struct inode *inode,
163
- struct list_head *mds_pages,
164
- int how,
165
- struct nfs_commit_info *cinfo);
166154
167155 int (*sync)(struct inode *inode, bool datasync);
168156
....@@ -185,6 +173,29 @@
185173 int (*prepare_layoutstats) (struct nfs42_layoutstat_args *args);
186174 };
187175
176
+struct pnfs_commit_ops {
177
+ void (*setup_ds_info)(struct pnfs_ds_commit_info *,
178
+ struct pnfs_layout_segment *);
179
+ void (*release_ds_info)(struct pnfs_ds_commit_info *,
180
+ struct inode *inode);
181
+ int (*commit_pagelist)(struct inode *inode,
182
+ struct list_head *mds_pages,
183
+ int how,
184
+ struct nfs_commit_info *cinfo);
185
+ void (*mark_request_commit) (struct nfs_page *req,
186
+ struct pnfs_layout_segment *lseg,
187
+ struct nfs_commit_info *cinfo,
188
+ u32 ds_commit_idx);
189
+ void (*clear_request_commit) (struct nfs_page *req,
190
+ struct nfs_commit_info *cinfo);
191
+ int (*scan_commit_lists) (struct nfs_commit_info *cinfo,
192
+ int max);
193
+ void (*recover_commit_reqs) (struct list_head *list,
194
+ struct nfs_commit_info *cinfo);
195
+ struct nfs_page * (*search_commit_reqs)(struct nfs_commit_info *cinfo,
196
+ struct page *page);
197
+};
198
+
188199 struct pnfs_layout_hdr {
189200 refcount_t plh_refcount;
190201 atomic_t plh_outstanding; /* number of RPCs out */
....@@ -200,8 +211,9 @@
200211 u32 plh_return_seq;
201212 enum pnfs_iomode plh_return_iomode;
202213 loff_t plh_lwb; /* last write byte for layoutcommit */
203
- struct rpc_cred *plh_lc_cred; /* layoutcommit cred */
214
+ const struct cred *plh_lc_cred; /* layoutcommit cred */
204215 struct inode *plh_inode;
216
+ struct rcu_head plh_rcu;
205217 };
206218
207219 struct pnfs_device {
....@@ -225,12 +237,14 @@
225237
226238 extern int pnfs_register_layoutdriver(struct pnfs_layoutdriver_type *);
227239 extern void pnfs_unregister_layoutdriver(struct pnfs_layoutdriver_type *);
240
+extern const struct pnfs_layoutdriver_type *pnfs_find_layoutdriver(u32 id);
241
+extern void pnfs_put_layoutdriver(const struct pnfs_layoutdriver_type *ld);
228242
229243 /* nfs4proc.c */
230244 extern size_t max_response_pages(struct nfs_server *server);
231245 extern int nfs4_proc_getdeviceinfo(struct nfs_server *server,
232246 struct pnfs_device *dev,
233
- struct rpc_cred *cred);
247
+ const struct cred *cred);
234248 extern struct pnfs_layout_segment* nfs4_proc_layoutget(struct nfs4_layoutget *lgp, long *timeout);
235249 extern int nfs4_proc_layoutreturn(struct nfs4_layoutreturn *lrp, bool sync);
236250
....@@ -241,6 +255,7 @@
241255 void set_pnfs_layoutdriver(struct nfs_server *, const struct nfs_fh *, struct nfs_fsinfo *);
242256 void unset_pnfs_layoutdriver(struct nfs_server *);
243257 void pnfs_generic_pg_check_layout(struct nfs_pageio_descriptor *pgio);
258
+void pnfs_generic_pg_check_range(struct nfs_pageio_descriptor *pgio, struct nfs_page *req);
244259 void pnfs_generic_pg_init_read(struct nfs_pageio_descriptor *, struct nfs_page *);
245260 int pnfs_generic_pg_readpages(struct nfs_pageio_descriptor *desc);
246261 void pnfs_generic_pg_init_write(struct nfs_pageio_descriptor *pgio,
....@@ -261,12 +276,13 @@
261276 bool is_recall);
262277 int pnfs_destroy_layouts_byclid(struct nfs_client *clp,
263278 bool is_recall);
264
-bool nfs4_layoutreturn_refresh_stateid(nfs4_stateid *dst,
279
+bool nfs4_layout_refresh_old_stateid(nfs4_stateid *dst,
265280 struct pnfs_layout_range *dst_range,
266281 struct inode *inode);
267282 void pnfs_put_layout_hdr(struct pnfs_layout_hdr *lo);
268283 void pnfs_set_layout_stateid(struct pnfs_layout_hdr *lo,
269284 const nfs4_stateid *new,
285
+ const struct cred *cred,
270286 bool update_barrier);
271287 int pnfs_mark_matching_lsegs_invalid(struct pnfs_layout_hdr *lo,
272288 struct list_head *tmp_list,
....@@ -281,7 +297,9 @@
281297 bool pnfs_roc(struct inode *ino,
282298 struct nfs4_layoutreturn_args *args,
283299 struct nfs4_layoutreturn_res *res,
284
- const struct rpc_cred *cred);
300
+ const struct cred *cred);
301
+int pnfs_roc_done(struct rpc_task *task, struct nfs4_layoutreturn_args **argpp,
302
+ struct nfs4_layoutreturn_res **respp, int *ret);
285303 void pnfs_roc_release(struct nfs4_layoutreturn_args *args,
286304 struct nfs4_layoutreturn_res *res,
287305 int ret);
....@@ -295,7 +313,7 @@
295313 int pnfs_commit_and_return_layout(struct inode *);
296314 void pnfs_ld_write_done(struct nfs_pgio_header *);
297315 void pnfs_ld_read_done(struct nfs_pgio_header *);
298
-void pnfs_read_resend_pnfs(struct nfs_pgio_header *);
316
+void pnfs_read_resend_pnfs(struct nfs_pgio_header *, unsigned int mirror_idx);
299317 struct pnfs_layout_segment *pnfs_update_layout(struct inode *ino,
300318 struct nfs_open_context *ctx,
301319 loff_t pos,
....@@ -322,6 +340,9 @@
322340 struct nfs4_threshold *pnfs_mdsthreshold_alloc(void);
323341 void pnfs_error_mark_layout_for_return(struct inode *inode,
324342 struct pnfs_layout_segment *lseg);
343
+void pnfs_layout_return_unused_byclid(struct nfs_client *clp,
344
+ enum pnfs_iomode iomode);
345
+
325346 /* nfs4_deviceid_flags */
326347 enum {
327348 NFS_DEVICEID_INVALID = 0, /* set when MDS clientid recalled */
....@@ -344,17 +365,28 @@
344365
345366 struct nfs4_deviceid_node *
346367 nfs4_find_get_deviceid(struct nfs_server *server,
347
- const struct nfs4_deviceid *id, struct rpc_cred *cred,
368
+ const struct nfs4_deviceid *id, const struct cred *cred,
348369 gfp_t gfp_mask);
349370 void nfs4_delete_deviceid(const struct pnfs_layoutdriver_type *, const struct nfs_client *, const struct nfs4_deviceid *);
350371 void nfs4_init_deviceid_node(struct nfs4_deviceid_node *, struct nfs_server *,
351372 const struct nfs4_deviceid *);
352373 bool nfs4_put_deviceid_node(struct nfs4_deviceid_node *);
374
+void nfs4_mark_deviceid_available(struct nfs4_deviceid_node *node);
353375 void nfs4_mark_deviceid_unavailable(struct nfs4_deviceid_node *node);
354376 bool nfs4_test_deviceid_unavailable(struct nfs4_deviceid_node *node);
355377 void nfs4_deviceid_purge_client(const struct nfs_client *);
356378
357379 /* pnfs_nfs.c */
380
+struct pnfs_commit_array *pnfs_alloc_commit_array(size_t n, gfp_t gfp_flags);
381
+void pnfs_free_commit_array(struct pnfs_commit_array *p);
382
+struct pnfs_commit_array *pnfs_add_commit_array(struct pnfs_ds_commit_info *,
383
+ struct pnfs_commit_array *,
384
+ struct pnfs_layout_segment *);
385
+
386
+void pnfs_generic_ds_cinfo_release_lseg(struct pnfs_ds_commit_info *fl_cinfo,
387
+ struct pnfs_layout_segment *lseg);
388
+void pnfs_generic_ds_cinfo_destroy(struct pnfs_ds_commit_info *fl_cinfo);
389
+
358390 void pnfs_generic_clear_request_commit(struct nfs_page *req,
359391 struct nfs_commit_info *cinfo);
360392 void pnfs_generic_commit_release(void *calldata);
....@@ -362,6 +394,8 @@
362394 void pnfs_generic_rw_release(void *data);
363395 void pnfs_generic_recover_commit_reqs(struct list_head *dst,
364396 struct nfs_commit_info *cinfo);
397
+struct nfs_page *pnfs_generic_search_commit_reqs(struct nfs_commit_info *cinfo,
398
+ struct page *page);
365399 int pnfs_generic_commit_pagelist(struct inode *inode,
366400 struct list_head *mds_pages,
367401 int how,
....@@ -433,9 +467,11 @@
433467 pnfs_commit_list(struct inode *inode, struct list_head *mds_pages, int how,
434468 struct nfs_commit_info *cinfo)
435469 {
436
- if (cinfo->ds == NULL || cinfo->ds->ncommitting == 0)
470
+ struct pnfs_ds_commit_info *fl_cinfo = cinfo->ds;
471
+
472
+ if (fl_cinfo == NULL || fl_cinfo->ncommitting == 0)
437473 return PNFS_NOT_ATTEMPTED;
438
- return NFS_SERVER(inode)->pnfs_curr_ld->commit_pagelist(inode, mds_pages, how, cinfo);
474
+ return fl_cinfo->ops->commit_pagelist(inode, mds_pages, how, cinfo);
439475 }
440476
441477 static inline struct pnfs_ds_commit_info *
....@@ -449,6 +485,28 @@
449485 }
450486
451487 static inline void
488
+pnfs_init_ds_commit_info_ops(struct pnfs_ds_commit_info *fl_cinfo, struct inode *inode)
489
+{
490
+ struct pnfs_ds_commit_info *inode_cinfo = pnfs_get_ds_info(inode);
491
+ if (inode_cinfo != NULL)
492
+ fl_cinfo->ops = inode_cinfo->ops;
493
+}
494
+
495
+static inline void
496
+pnfs_init_ds_commit_info(struct pnfs_ds_commit_info *fl_cinfo)
497
+{
498
+ INIT_LIST_HEAD(&fl_cinfo->commits);
499
+ fl_cinfo->ops = NULL;
500
+}
501
+
502
+static inline void
503
+pnfs_release_ds_info(struct pnfs_ds_commit_info *fl_cinfo, struct inode *inode)
504
+{
505
+ if (fl_cinfo->ops != NULL && fl_cinfo->ops->release_ds_info != NULL)
506
+ fl_cinfo->ops->release_ds_info(fl_cinfo, inode);
507
+}
508
+
509
+static inline void
452510 pnfs_generic_mark_devid_invalid(struct nfs4_deviceid_node *node)
453511 {
454512 set_bit(NFS_DEVICEID_INVALID, &node->flags);
....@@ -458,24 +516,22 @@
458516 pnfs_mark_request_commit(struct nfs_page *req, struct pnfs_layout_segment *lseg,
459517 struct nfs_commit_info *cinfo, u32 ds_commit_idx)
460518 {
461
- struct inode *inode = d_inode(req->wb_context->dentry);
462
- struct pnfs_layoutdriver_type *ld = NFS_SERVER(inode)->pnfs_curr_ld;
519
+ struct pnfs_ds_commit_info *fl_cinfo = cinfo->ds;
463520
464
- if (lseg == NULL || ld->mark_request_commit == NULL)
521
+ if (!lseg || !fl_cinfo->ops || !fl_cinfo->ops->mark_request_commit)
465522 return false;
466
- ld->mark_request_commit(req, lseg, cinfo, ds_commit_idx);
523
+ fl_cinfo->ops->mark_request_commit(req, lseg, cinfo, ds_commit_idx);
467524 return true;
468525 }
469526
470527 static inline bool
471528 pnfs_clear_request_commit(struct nfs_page *req, struct nfs_commit_info *cinfo)
472529 {
473
- struct inode *inode = d_inode(req->wb_context->dentry);
474
- struct pnfs_layoutdriver_type *ld = NFS_SERVER(inode)->pnfs_curr_ld;
530
+ struct pnfs_ds_commit_info *fl_cinfo = cinfo->ds;
475531
476
- if (ld == NULL || ld->clear_request_commit == NULL)
532
+ if (!fl_cinfo || !fl_cinfo->ops || !fl_cinfo->ops->clear_request_commit)
477533 return false;
478
- ld->clear_request_commit(req, cinfo);
534
+ fl_cinfo->ops->clear_request_commit(req, cinfo);
479535 return true;
480536 }
481537
....@@ -483,21 +539,31 @@
483539 pnfs_scan_commit_lists(struct inode *inode, struct nfs_commit_info *cinfo,
484540 int max)
485541 {
486
- if (cinfo->ds == NULL || cinfo->ds->nwritten == 0)
542
+ struct pnfs_ds_commit_info *fl_cinfo = cinfo->ds;
543
+
544
+ if (!fl_cinfo || fl_cinfo->nwritten == 0)
487545 return 0;
488
- else
489
- return NFS_SERVER(inode)->pnfs_curr_ld->scan_commit_lists(cinfo, max);
546
+ return fl_cinfo->ops->scan_commit_lists(cinfo, max);
547
+}
548
+
549
+static inline void
550
+pnfs_recover_commit_reqs(struct list_head *head, struct nfs_commit_info *cinfo)
551
+{
552
+ struct pnfs_ds_commit_info *fl_cinfo = cinfo->ds;
553
+
554
+ if (fl_cinfo && fl_cinfo->nwritten != 0)
555
+ fl_cinfo->ops->recover_commit_reqs(head, cinfo);
490556 }
491557
492558 static inline struct nfs_page *
493559 pnfs_search_commit_reqs(struct inode *inode, struct nfs_commit_info *cinfo,
494560 struct page *page)
495561 {
496
- struct pnfs_layoutdriver_type *ld = NFS_SERVER(inode)->pnfs_curr_ld;
562
+ struct pnfs_ds_commit_info *fl_cinfo = cinfo->ds;
497563
498
- if (ld == NULL || ld->search_commit_reqs == NULL)
564
+ if (!fl_cinfo->ops || !fl_cinfo->ops->search_commit_reqs)
499565 return NULL;
500
- return ld->search_commit_reqs(cinfo, page);
566
+ return fl_cinfo->ops->search_commit_reqs(cinfo, page);
501567 }
502568
503569 /* Should the pNFS client commit and return the layout upon a setattr */
....@@ -699,9 +765,18 @@
699765 pnfs_roc(struct inode *ino,
700766 struct nfs4_layoutreturn_args *args,
701767 struct nfs4_layoutreturn_res *res,
702
- const struct rpc_cred *cred)
768
+ const struct cred *cred)
703769 {
704770 return false;
771
+}
772
+
773
+static inline int
774
+pnfs_roc_done(struct rpc_task *task,
775
+ struct nfs4_layoutreturn_args **argpp,
776
+ struct nfs4_layoutreturn_res **respp,
777
+ int *ret)
778
+{
779
+ return 0;
705780 }
706781
707782 static inline void
....@@ -740,6 +815,21 @@
740815 return NULL;
741816 }
742817
818
+static inline void
819
+pnfs_init_ds_commit_info_ops(struct pnfs_ds_commit_info *fl_cinfo, struct inode *inode)
820
+{
821
+}
822
+
823
+static inline void
824
+pnfs_init_ds_commit_info(struct pnfs_ds_commit_info *fl_cinfo)
825
+{
826
+}
827
+
828
+static inline void
829
+pnfs_release_ds_info(struct pnfs_ds_commit_info *fl_cinfo, struct inode *inode)
830
+{
831
+}
832
+
743833 static inline bool
744834 pnfs_mark_request_commit(struct nfs_page *req, struct pnfs_layout_segment *lseg,
745835 struct nfs_commit_info *cinfo, u32 ds_commit_idx)
....@@ -758,6 +848,11 @@
758848 int max)
759849 {
760850 return 0;
851
+}
852
+
853
+static inline void
854
+pnfs_recover_commit_reqs(struct list_head *head, struct nfs_commit_info *cinfo)
855
+{
761856 }
762857
763858 static inline struct nfs_page *
....@@ -788,7 +883,7 @@
788883 {
789884 }
790885
791
-static inline bool nfs4_layoutreturn_refresh_stateid(nfs4_stateid *dst,
886
+static inline bool nfs4_layout_refresh_old_stateid(nfs4_stateid *dst,
792887 struct pnfs_layout_range *dst_range,
793888 struct inode *inode)
794889 {