Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'nfs-for-6.15-2' of git://git.linux-nfs.org/projects/trondmy/linux-nfs

Pull NFS client bugfixes from Trond Myklebust:

- NFS: Fix a couple of missed handlers for the ENETDOWN and ENETUNREACH
transport errors

- NFS: Handle Oopsable failure of nfs_get_lock_context in the unlock
path

- NFSv4: Fix a race in nfs_local_open_fh()

- NFSv4/pNFS: Fix a couple of layout segment leaks in layoutreturn

- NFSv4/pNFS Avoid sharing pNFS DS connections between net namespaces
since IP addresses are not guaranteed to refer to the same nodes

- NFS: Don't flush file data while holding multiple directory locks in
nfs_rename()

* tag 'nfs-for-6.15-2' of git://git.linux-nfs.org/projects/trondmy/linux-nfs:
NFS: Avoid flushing data while holding directory locks in nfs_rename()
NFS/pnfs: Fix the error path in pnfs_layoutreturn_retry_later_locked()
NFSv4/pnfs: Reset the layout state after a layoutreturn
NFS/localio: Fix a race in nfs_local_open_fh()
nfs: nfs3acl: drop useless assignment in nfs3_get_acl()
nfs: direct: drop useless initializer in nfs_direct_write_completion()
nfs: move the nfs4_data_server_cache into struct nfs_net
nfs: don't share pNFS DS connections between net namespaces
nfs: handle failure of nfs_get_lock_context in unlock path
pNFS/flexfiles: Record the RPC errors in the I/O tracepoints
NFSv4/pnfs: Layoutreturn on close must handle fatal networking errors
NFSv4: Handle fatal ENETDOWN and ENETUNREACH errors

+143 -62
+9
fs/nfs/client.c
··· 1105 1105 if (server->namelen == 0 || server->namelen > NFS2_MAXNAMLEN) 1106 1106 server->namelen = NFS2_MAXNAMLEN; 1107 1107 } 1108 + /* Linux 'subtree_check' borkenness mandates this setting */ 1109 + server->fh_expire_type = NFS_FH_VOL_RENAME; 1108 1110 1109 1111 if (!(fattr->valid & NFS_ATTR_FATTR)) { 1110 1112 error = ctx->nfs_mod->rpc_ops->getattr(server, ctx->mntfh, ··· 1202 1200 #if IS_ENABLED(CONFIG_NFS_V4) 1203 1201 idr_init(&nn->cb_ident_idr); 1204 1202 #endif 1203 + #if IS_ENABLED(CONFIG_NFS_V4_1) 1204 + INIT_LIST_HEAD(&nn->nfs4_data_server_cache); 1205 + spin_lock_init(&nn->nfs4_data_server_lock); 1206 + #endif 1205 1207 spin_lock_init(&nn->nfs_client_lock); 1206 1208 nn->boot_time = ktime_get_real(); 1207 1209 memset(&nn->rpcstats, 0, sizeof(nn->rpcstats)); ··· 1222 1216 nfs_cleanup_cb_ident_idr(net); 1223 1217 WARN_ON_ONCE(!list_empty(&nn->nfs_client_list)); 1224 1218 WARN_ON_ONCE(!list_empty(&nn->nfs_volume_list)); 1219 + #if IS_ENABLED(CONFIG_NFS_V4_1) 1220 + WARN_ON_ONCE(!list_empty(&nn->nfs4_data_server_cache)); 1221 + #endif 1225 1222 } 1226 1223 1227 1224 #ifdef CONFIG_PROC_FS
+14 -1
fs/nfs/dir.c
··· 2676 2676 unblock_revalidate(new_dentry); 2677 2677 } 2678 2678 2679 + static bool nfs_rename_is_unsafe_cross_dir(struct dentry *old_dentry, 2680 + struct dentry *new_dentry) 2681 + { 2682 + struct nfs_server *server = NFS_SB(old_dentry->d_sb); 2683 + 2684 + if (old_dentry->d_parent != new_dentry->d_parent) 2685 + return false; 2686 + if (server->fh_expire_type & NFS_FH_RENAME_UNSAFE) 2687 + return !(server->fh_expire_type & NFS_FH_NOEXPIRE_WITH_OPEN); 2688 + return true; 2689 + } 2690 + 2679 2691 /* 2680 2692 * RENAME 2681 2693 * FIXME: Some nfsds, like the Linux user space nfsd, may generate a ··· 2775 2763 2776 2764 } 2777 2765 2778 - if (S_ISREG(old_inode->i_mode)) 2766 + if (S_ISREG(old_inode->i_mode) && 2767 + nfs_rename_is_unsafe_cross_dir(old_dentry, new_dentry)) 2779 2768 nfs_sync_inode(old_inode); 2780 2769 task = nfs_async_rename(old_dir, new_dir, old_dentry, new_dentry, 2781 2770 must_unblock ? nfs_unblock_rename : NULL);
+1 -1
fs/nfs/direct.c
··· 757 757 { 758 758 struct nfs_direct_req *dreq = hdr->dreq; 759 759 struct nfs_commit_info cinfo; 760 - struct nfs_page *req = nfs_list_entry(hdr->pages.next); 761 760 struct inode *inode = dreq->inode; 762 761 int flags = NFS_ODIRECT_DONE; 763 762 ··· 785 786 spin_unlock(&inode->i_lock); 786 787 787 788 while (!list_empty(&hdr->pages)) { 789 + struct nfs_page *req; 788 790 789 791 req = nfs_list_entry(hdr->pages.next); 790 792 nfs_list_remove_request(req);
+3 -3
fs/nfs/filelayout/filelayoutdev.c
··· 76 76 struct page *scratch; 77 77 struct list_head dsaddrs; 78 78 struct nfs4_pnfs_ds_addr *da; 79 + struct net *net = server->nfs_client->cl_net; 79 80 80 81 /* set up xdr stream */ 81 82 scratch = alloc_page(gfp_flags); ··· 160 159 161 160 mp_count = be32_to_cpup(p); /* multipath count */ 162 161 for (j = 0; j < mp_count; j++) { 163 - da = nfs4_decode_mp_ds_addr(server->nfs_client->cl_net, 164 - &stream, gfp_flags); 162 + da = nfs4_decode_mp_ds_addr(net, &stream, gfp_flags); 165 163 if (da) 166 164 list_add_tail(&da->da_node, &dsaddrs); 167 165 } ··· 170 170 goto out_err_free_deviceid; 171 171 } 172 172 173 - dsaddr->ds_list[i] = nfs4_pnfs_ds_add(&dsaddrs, gfp_flags); 173 + dsaddr->ds_list[i] = nfs4_pnfs_ds_add(net, &dsaddrs, gfp_flags); 174 174 if (!dsaddr->ds_list[i]) 175 175 goto out_err_drain_dsaddrs; 176 176 trace_fl_getdevinfo(server, &pdev->dev_id, dsaddr->ds_list[i]->ds_remotestr);
+3 -3
fs/nfs/flexfilelayout/flexfilelayout.c
··· 1329 1329 hdr->args.offset, hdr->args.count, 1330 1330 &hdr->res.op_status, OP_READ, 1331 1331 task->tk_status); 1332 - trace_ff_layout_read_error(hdr); 1332 + trace_ff_layout_read_error(hdr, task->tk_status); 1333 1333 } 1334 1334 1335 1335 err = ff_layout_async_handle_error(task, hdr->args.context->state, ··· 1502 1502 hdr->args.offset, hdr->args.count, 1503 1503 &hdr->res.op_status, OP_WRITE, 1504 1504 task->tk_status); 1505 - trace_ff_layout_write_error(hdr); 1505 + trace_ff_layout_write_error(hdr, task->tk_status); 1506 1506 } 1507 1507 1508 1508 err = ff_layout_async_handle_error(task, hdr->args.context->state, ··· 1551 1551 data->args.offset, data->args.count, 1552 1552 &data->res.op_status, OP_COMMIT, 1553 1553 task->tk_status); 1554 - trace_ff_layout_commit_error(data); 1554 + trace_ff_layout_commit_error(data, task->tk_status); 1555 1555 } 1556 1556 1557 1557 err = ff_layout_async_handle_error(task, NULL, data->ds_clp,
+3 -3
fs/nfs/flexfilelayout/flexfilelayoutdev.c
··· 49 49 struct nfs4_pnfs_ds_addr *da; 50 50 struct nfs4_ff_layout_ds *new_ds = NULL; 51 51 struct nfs4_ff_ds_version *ds_versions = NULL; 52 + struct net *net = server->nfs_client->cl_net; 52 53 u32 mp_count; 53 54 u32 version_count; 54 55 __be32 *p; ··· 81 80 82 81 for (i = 0; i < mp_count; i++) { 83 82 /* multipath ds */ 84 - da = nfs4_decode_mp_ds_addr(server->nfs_client->cl_net, 85 - &stream, gfp_flags); 83 + da = nfs4_decode_mp_ds_addr(net, &stream, gfp_flags); 86 84 if (da) 87 85 list_add_tail(&da->da_node, &dsaddrs); 88 86 } ··· 149 149 new_ds->ds_versions = ds_versions; 150 150 new_ds->ds_versions_cnt = version_count; 151 151 152 - new_ds->ds = nfs4_pnfs_ds_add(&dsaddrs, gfp_flags); 152 + new_ds->ds = nfs4_pnfs_ds_add(net, &dsaddrs, gfp_flags); 153 153 if (!new_ds->ds) 154 154 goto out_err_drain_dsaddrs; 155 155
+1 -1
fs/nfs/localio.c
··· 278 278 new = __nfs_local_open_fh(clp, cred, fh, nfl, mode); 279 279 if (IS_ERR(new)) 280 280 return NULL; 281 + rcu_read_lock(); 281 282 /* try to swap in the pointer */ 282 283 spin_lock(&clp->cl_uuid.lock); 283 284 nf = rcu_dereference_protected(*pnf, 1); ··· 288 287 rcu_assign_pointer(*pnf, nf); 289 288 } 290 289 spin_unlock(&clp->cl_uuid.lock); 291 - rcu_read_lock(); 292 290 } 293 291 nf = nfs_local_file_get(nf); 294 292 rcu_read_unlock();
+5 -1
fs/nfs/netns.h
··· 31 31 unsigned short nfs_callback_tcpport; 32 32 unsigned short nfs_callback_tcpport6; 33 33 int cb_users[NFS4_MAX_MINOR_VERSION + 1]; 34 - #endif 34 + #endif /* CONFIG_NFS_V4 */ 35 + #if IS_ENABLED(CONFIG_NFS_V4_1) 36 + struct list_head nfs4_data_server_cache; 37 + spinlock_t nfs4_data_server_lock; 38 + #endif /* CONFIG_NFS_V4_1 */ 35 39 struct nfs_netns_client *nfs_client; 36 40 spinlock_t nfs_client_lock; 37 41 ktime_t boot_time;
+1 -1
fs/nfs/nfs3acl.c
··· 104 104 105 105 switch (status) { 106 106 case 0: 107 - status = nfs_refresh_inode(inode, res.fattr); 107 + nfs_refresh_inode(inode, res.fattr); 108 108 break; 109 109 case -EPFNOSUPPORT: 110 110 case -EPROTONOSUPPORT:
+17 -1
fs/nfs/nfs4proc.c
··· 671 671 struct nfs_client *clp = server->nfs_client; 672 672 int ret; 673 673 674 + if ((task->tk_rpc_status == -ENETDOWN || 675 + task->tk_rpc_status == -ENETUNREACH) && 676 + task->tk_flags & RPC_TASK_NETUNREACH_FATAL) { 677 + exception->delay = 0; 678 + exception->recovering = 0; 679 + exception->retry = 0; 680 + return -EIO; 681 + } 682 + 674 683 ret = nfs4_do_handle_exception(server, errorcode, exception); 675 684 if (exception->delay) { 676 685 int ret2 = nfs4_exception_should_retrans(server, exception); ··· 7083 7074 struct nfs4_unlockdata *p; 7084 7075 struct nfs4_state *state = lsp->ls_state; 7085 7076 struct inode *inode = state->inode; 7077 + struct nfs_lock_context *l_ctx; 7086 7078 7087 7079 p = kzalloc(sizeof(*p), GFP_KERNEL); 7088 7080 if (p == NULL) 7089 7081 return NULL; 7082 + l_ctx = nfs_get_lock_context(ctx); 7083 + if (!IS_ERR(l_ctx)) { 7084 + p->l_ctx = l_ctx; 7085 + } else { 7086 + kfree(p); 7087 + return NULL; 7088 + } 7090 7089 p->arg.fh = NFS_FH(inode); 7091 7090 p->arg.fl = &p->fl; 7092 7091 p->arg.seqid = seqid; ··· 7102 7085 p->lsp = lsp; 7103 7086 /* Ensure we don't close file until we're done freeing locks! */ 7104 7087 p->ctx = get_nfs_open_context(ctx); 7105 - p->l_ctx = nfs_get_lock_context(ctx); 7106 7088 locks_init_lock(&p->fl); 7107 7089 locks_copy_lock(&p->fl, fl); 7108 7090 p->server = NFS_SERVER(inode);
+22 -12
fs/nfs/nfs4trace.h
··· 2051 2051 2052 2052 DECLARE_EVENT_CLASS(nfs4_flexfiles_io_event, 2053 2053 TP_PROTO( 2054 - const struct nfs_pgio_header *hdr 2054 + const struct nfs_pgio_header *hdr, 2055 + int error 2055 2056 ), 2056 2057 2057 - TP_ARGS(hdr), 2058 + TP_ARGS(hdr, error), 2058 2059 2059 2060 TP_STRUCT__entry( 2060 2061 __field(unsigned long, error) 2062 + __field(unsigned long, nfs_error) 2061 2063 __field(dev_t, dev) 2062 2064 __field(u32, fhandle) 2063 2065 __field(u64, fileid) ··· 2075 2073 TP_fast_assign( 2076 2074 const struct inode *inode = hdr->inode; 2077 2075 2078 - __entry->error = hdr->res.op_status; 2076 + __entry->error = -error; 2077 + __entry->nfs_error = hdr->res.op_status; 2079 2078 __entry->fhandle = nfs_fhandle_hash(hdr->args.fh); 2080 2079 __entry->fileid = NFS_FILEID(inode); 2081 2080 __entry->dev = inode->i_sb->s_dev; ··· 2091 2088 2092 2089 TP_printk( 2093 2090 "error=%ld (%s) fileid=%02x:%02x:%llu fhandle=0x%08x " 2094 - "offset=%llu count=%u stateid=%d:0x%08x dstaddr=%s", 2091 + "offset=%llu count=%u stateid=%d:0x%08x dstaddr=%s " 2092 + "nfs_error=%lu (%s)", 2095 2093 -__entry->error, 2096 2094 show_nfs4_status(__entry->error), 2097 2095 MAJOR(__entry->dev), MINOR(__entry->dev), ··· 2100 2096 __entry->fhandle, 2101 2097 __entry->offset, __entry->count, 2102 2098 __entry->stateid_seq, __entry->stateid_hash, 2103 - __get_str(dstaddr) 2099 + __get_str(dstaddr), __entry->nfs_error, 2100 + show_nfs4_status(__entry->nfs_error) 2104 2101 ) 2105 2102 ); 2106 2103 2107 2104 #define DEFINE_NFS4_FLEXFILES_IO_EVENT(name) \ 2108 2105 DEFINE_EVENT(nfs4_flexfiles_io_event, name, \ 2109 2106 TP_PROTO( \ 2110 - const struct nfs_pgio_header *hdr \ 2107 + const struct nfs_pgio_header *hdr, \ 2108 + int error \ 2111 2109 ), \ 2112 - TP_ARGS(hdr)) 2110 + TP_ARGS(hdr, error)) 2113 2111 DEFINE_NFS4_FLEXFILES_IO_EVENT(ff_layout_read_error); 2114 2112 DEFINE_NFS4_FLEXFILES_IO_EVENT(ff_layout_write_error); 2115 2113 2116 2114 TRACE_EVENT(ff_layout_commit_error, 2117 2115 TP_PROTO( 2118 - const struct nfs_commit_data *data 2116 + const struct nfs_commit_data *data, 2117 + int error 2119 2118 ), 2120 2119 2121 - TP_ARGS(data), 2120 + TP_ARGS(data, error), 2122 2121 2123 2122 TP_STRUCT__entry( 2124 2123 __field(unsigned long, error) 2124 + __field(unsigned long, nfs_error) 2125 2125 __field(dev_t, dev) 2126 2126 __field(u32, fhandle) 2127 2127 __field(u64, fileid) ··· 2139 2131 TP_fast_assign( 2140 2132 const struct inode *inode = data->inode; 2141 2133 2142 - __entry->error = data->res.op_status; 2134 + __entry->error = -error; 2135 + __entry->nfs_error = data->res.op_status; 2143 2136 __entry->fhandle = nfs_fhandle_hash(data->args.fh); 2144 2137 __entry->fileid = NFS_FILEID(inode); 2145 2138 __entry->dev = inode->i_sb->s_dev; ··· 2151 2142 2152 2143 TP_printk( 2153 2144 "error=%ld (%s) fileid=%02x:%02x:%llu fhandle=0x%08x " 2154 - "offset=%llu count=%u dstaddr=%s", 2145 + "offset=%llu count=%u dstaddr=%s nfs_error=%lu (%s)", 2155 2146 -__entry->error, 2156 2147 show_nfs4_status(__entry->error), 2157 2148 MAJOR(__entry->dev), MINOR(__entry->dev), 2158 2149 (unsigned long long)__entry->fileid, 2159 2150 __entry->fhandle, 2160 2151 __entry->offset, __entry->count, 2161 - __get_str(dstaddr) 2152 + __get_str(dstaddr), __entry->nfs_error, 2153 + show_nfs4_status(__entry->nfs_error) 2162 2154 ) 2163 2155 ); 2164 2156
+34 -17
fs/nfs/pnfs.c
··· 745 745 return remaining; 746 746 } 747 747 748 + static void pnfs_reset_return_info(struct pnfs_layout_hdr *lo) 749 + { 750 + struct pnfs_layout_segment *lseg; 751 + 752 + list_for_each_entry(lseg, &lo->plh_return_segs, pls_list) 753 + pnfs_set_plh_return_info(lo, lseg->pls_range.iomode, 0); 754 + } 755 + 748 756 static void 749 757 pnfs_free_returned_lsegs(struct pnfs_layout_hdr *lo, 750 758 struct list_head *free_me, ··· 1254 1246 static void 1255 1247 pnfs_layoutreturn_retry_later_locked(struct pnfs_layout_hdr *lo, 1256 1248 const nfs4_stateid *arg_stateid, 1257 - const struct pnfs_layout_range *range) 1249 + const struct pnfs_layout_range *range, 1250 + struct list_head *freeme) 1258 1251 { 1259 - const struct pnfs_layout_segment *lseg; 1260 - u32 seq = be32_to_cpu(arg_stateid->seqid); 1261 - 1262 1252 if (pnfs_layout_is_valid(lo) && 1263 - nfs4_stateid_match_other(&lo->plh_stateid, arg_stateid)) { 1264 - list_for_each_entry(lseg, &lo->plh_return_segs, pls_list) { 1265 - if (pnfs_seqid_is_newer(lseg->pls_seq, seq) || 1266 - !pnfs_should_free_range(&lseg->pls_range, range)) 1267 - continue; 1268 - pnfs_set_plh_return_info(lo, range->iomode, seq); 1269 - break; 1270 - } 1271 - } 1253 + nfs4_stateid_match_other(&lo->plh_stateid, arg_stateid)) 1254 + pnfs_reset_return_info(lo); 1255 + else 1256 + pnfs_mark_layout_stateid_invalid(lo, freeme); 1257 + pnfs_clear_layoutreturn_waitbit(lo); 1272 1258 } 1273 1259 1274 1260 void pnfs_layoutreturn_retry_later(struct pnfs_layout_hdr *lo, ··· 1270 1268 const struct pnfs_layout_range *range) 1271 1269 { 1272 1270 struct inode *inode = lo->plh_inode; 1271 + LIST_HEAD(freeme); 1273 1272 1274 1273 spin_lock(&inode->i_lock); 1275 - pnfs_layoutreturn_retry_later_locked(lo, arg_stateid, range); 1276 - pnfs_clear_layoutreturn_waitbit(lo); 1274 + pnfs_layoutreturn_retry_later_locked(lo, arg_stateid, range, &freeme); 1277 1275 spin_unlock(&inode->i_lock); 1276 + pnfs_free_lseg_list(&freeme); 1278 1277 } 1279 1278 1280 1279 void pnfs_layoutreturn_free_lsegs(struct pnfs_layout_hdr *lo, ··· 1295 1292 pnfs_mark_matching_lsegs_invalid(lo, &freeme, range, seq); 1296 1293 pnfs_free_returned_lsegs(lo, &freeme, range, seq); 1297 1294 pnfs_set_layout_stateid(lo, stateid, NULL, true); 1295 + pnfs_reset_return_info(lo); 1298 1296 } else 1299 1297 pnfs_mark_layout_stateid_invalid(lo, &freeme); 1300 1298 out_unlock: ··· 1665 1661 /* Was there an RPC level error? If not, retry */ 1666 1662 if (task->tk_rpc_status == 0) 1667 1663 break; 1664 + /* 1665 + * Is there a fatal network level error? 1666 + * If so release the layout, but flag the error. 1667 + */ 1668 + if ((task->tk_rpc_status == -ENETDOWN || 1669 + task->tk_rpc_status == -ENETUNREACH) && 1670 + task->tk_flags & RPC_TASK_NETUNREACH_FATAL) { 1671 + *ret = 0; 1672 + (*respp)->lrs_present = 0; 1673 + retval = -EIO; 1674 + break; 1675 + } 1668 1676 /* If the call was not sent, let caller handle it */ 1669 1677 if (!RPC_WAS_SENT(task)) 1670 1678 return 0; ··· 1711 1695 struct inode *inode = args->inode; 1712 1696 const nfs4_stateid *res_stateid = NULL; 1713 1697 struct nfs4_xdr_opaque_data *ld_private = args->ld_private; 1698 + LIST_HEAD(freeme); 1714 1699 1715 1700 switch (ret) { 1716 1701 case -NFS4ERR_BADSESSION: ··· 1720 1703 case -NFS4ERR_NOMATCHING_LAYOUT: 1721 1704 spin_lock(&inode->i_lock); 1722 1705 pnfs_layoutreturn_retry_later_locked(lo, &args->stateid, 1723 - &args->range); 1724 - pnfs_clear_layoutreturn_waitbit(lo); 1706 + &args->range, &freeme); 1725 1707 spin_unlock(&inode->i_lock); 1708 + pnfs_free_lseg_list(&freeme); 1726 1709 break; 1727 1710 case 0: 1728 1711 if (res->lrs_present)
+3 -1
fs/nfs/pnfs.h
··· 60 60 struct list_head ds_node; /* nfs4_pnfs_dev_hlist dev_dslist */ 61 61 char *ds_remotestr; /* comma sep list of addrs */ 62 62 struct list_head ds_addrs; 63 + const struct net *ds_net; 63 64 struct nfs_client *ds_clp; 64 65 refcount_t ds_count; 65 66 unsigned long ds_state; ··· 416 415 int pnfs_generic_scan_commit_lists(struct nfs_commit_info *cinfo, int max); 417 416 void pnfs_generic_write_commit_done(struct rpc_task *task, void *data); 418 417 void nfs4_pnfs_ds_put(struct nfs4_pnfs_ds *ds); 419 - struct nfs4_pnfs_ds *nfs4_pnfs_ds_add(struct list_head *dsaddrs, 418 + struct nfs4_pnfs_ds *nfs4_pnfs_ds_add(const struct net *net, 419 + struct list_head *dsaddrs, 420 420 gfp_t gfp_flags); 421 421 void nfs4_pnfs_v3_ds_connect_unload(void); 422 422 int nfs4_pnfs_ds_connect(struct nfs_server *mds_srv, struct nfs4_pnfs_ds *ds,
+18 -14
fs/nfs/pnfs_nfs.c
··· 16 16 #include "nfs4session.h" 17 17 #include "internal.h" 18 18 #include "pnfs.h" 19 + #include "netns.h" 19 20 20 21 #define NFSDBG_FACILITY NFSDBG_PNFS 21 22 ··· 505 504 /* 506 505 * Data server cache 507 506 * 508 - * Data servers can be mapped to different device ids. 509 - * nfs4_pnfs_ds reference counting 507 + * Data servers can be mapped to different device ids, but should 508 + * never be shared between net namespaces. 509 + * 510 + * nfs4_pnfs_ds reference counting: 510 511 * - set to 1 on allocation 511 512 * - incremented when a device id maps a data server already in the cache. 512 513 * - decremented when deviceid is removed from the cache. 513 514 */ 514 - static DEFINE_SPINLOCK(nfs4_ds_cache_lock); 515 - static LIST_HEAD(nfs4_data_server_cache); 516 515 517 516 /* Debug routines */ 518 517 static void ··· 605 604 * Lookup DS by addresses. nfs4_ds_cache_lock is held 606 605 */ 607 606 static struct nfs4_pnfs_ds * 608 - _data_server_lookup_locked(const struct list_head *dsaddrs) 607 + _data_server_lookup_locked(const struct nfs_net *nn, const struct list_head *dsaddrs) 609 608 { 610 609 struct nfs4_pnfs_ds *ds; 611 610 612 - list_for_each_entry(ds, &nfs4_data_server_cache, ds_node) 611 + list_for_each_entry(ds, &nn->nfs4_data_server_cache, ds_node) 613 612 if (_same_data_server_addrs_locked(&ds->ds_addrs, dsaddrs)) 614 613 return ds; 615 614 return NULL; ··· 654 653 655 654 void nfs4_pnfs_ds_put(struct nfs4_pnfs_ds *ds) 656 655 { 657 - if (refcount_dec_and_lock(&ds->ds_count, 658 - &nfs4_ds_cache_lock)) { 656 + struct nfs_net *nn = net_generic(ds->ds_net, nfs_net_id); 657 + 658 + if (refcount_dec_and_lock(&ds->ds_count, &nn->nfs4_data_server_lock)) { 659 659 list_del_init(&ds->ds_node); 660 - spin_unlock(&nfs4_ds_cache_lock); 660 + spin_unlock(&nn->nfs4_data_server_lock); 661 661 destroy_ds(ds); 662 662 } 663 663 } ··· 718 716 * uncached and return cached struct nfs4_pnfs_ds. 719 717 */ 720 718 struct nfs4_pnfs_ds * 721 - nfs4_pnfs_ds_add(struct list_head *dsaddrs, gfp_t gfp_flags) 719 + nfs4_pnfs_ds_add(const struct net *net, struct list_head *dsaddrs, gfp_t gfp_flags) 722 720 { 721 + struct nfs_net *nn = net_generic(net, nfs_net_id); 723 722 struct nfs4_pnfs_ds *tmp_ds, *ds = NULL; 724 723 char *remotestr; 725 724 ··· 736 733 /* this is only used for debugging, so it's ok if its NULL */ 737 734 remotestr = nfs4_pnfs_remotestr(dsaddrs, gfp_flags); 738 735 739 - spin_lock(&nfs4_ds_cache_lock); 740 - tmp_ds = _data_server_lookup_locked(dsaddrs); 736 + spin_lock(&nn->nfs4_data_server_lock); 737 + tmp_ds = _data_server_lookup_locked(nn, dsaddrs); 741 738 if (tmp_ds == NULL) { 742 739 INIT_LIST_HEAD(&ds->ds_addrs); 743 740 list_splice_init(dsaddrs, &ds->ds_addrs); 744 741 ds->ds_remotestr = remotestr; 745 742 refcount_set(&ds->ds_count, 1); 746 743 INIT_LIST_HEAD(&ds->ds_node); 744 + ds->ds_net = net; 747 745 ds->ds_clp = NULL; 748 - list_add(&ds->ds_node, &nfs4_data_server_cache); 746 + list_add(&ds->ds_node, &nn->nfs4_data_server_cache); 749 747 dprintk("%s add new data server %s\n", __func__, 750 748 ds->ds_remotestr); 751 749 } else { ··· 758 754 refcount_read(&tmp_ds->ds_count)); 759 755 ds = tmp_ds; 760 756 } 761 - spin_unlock(&nfs4_ds_cache_lock); 757 + spin_unlock(&nn->nfs4_data_server_lock); 762 758 out: 763 759 return ds; 764 760 }
+9 -3
include/linux/nfs_fs_sb.h
··· 213 213 char *fscache_uniq; /* Uniquifier (or NULL) */ 214 214 #endif 215 215 216 + /* The following #defines numerically match the NFSv4 equivalents */ 217 + #define NFS_FH_NOEXPIRE_WITH_OPEN (0x1) 218 + #define NFS_FH_VOLATILE_ANY (0x2) 219 + #define NFS_FH_VOL_MIGRATION (0x4) 220 + #define NFS_FH_VOL_RENAME (0x8) 221 + #define NFS_FH_RENAME_UNSAFE (NFS_FH_VOLATILE_ANY | NFS_FH_VOL_RENAME) 222 + u32 fh_expire_type; /* V4 bitmask representing file 223 + handle volatility type for 224 + this filesystem */ 216 225 u32 pnfs_blksize; /* layout_blksize attr */ 217 226 #if IS_ENABLED(CONFIG_NFS_V4) 218 227 u32 attr_bitmask[3];/* V4 bitmask representing the set ··· 245 236 u32 acl_bitmask; /* V4 bitmask representing the ACEs 246 237 that are supported on this 247 238 filesystem */ 248 - u32 fh_expire_type; /* V4 bitmask representing file 249 - handle volatility type for 250 - this filesystem */ 251 239 struct pnfs_layoutdriver_type *pnfs_curr_ld; /* Active layout driver */ 252 240 struct rpc_wait_queue roc_rpcwaitq; 253 241 void *pnfs_ld_data; /* per mount point data */