diff options
author | Weston Andros Adamson <dros@netapp.com> | 2011-06-01 16:44:44 -0400 |
---|---|---|
committer | Trond Myklebust <Trond.Myklebust@netapp.com> | 2011-07-12 13:40:27 -0400 |
commit | 6382a44138e7aa40bf52170e7afc014443a24806 (patch) | |
tree | 9126d01d1fe2442fea057c3f45e4e3e532c85424 /fs/nfs/callback_proc.c | |
parent | 35dbbc99e93e57680837c17f96efe370f0535064 (diff) |
NFS: move pnfs layouts to nfs_server structure
Layouts should be tracked per nfs_server (aka superblock)
instead of per struct nfs_client, which may have multiple FSIDs associated
with it.
Signed-off-by: Weston Andros Adamson <dros@netapp.com>
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Diffstat (limited to 'fs/nfs/callback_proc.c')
-rw-r--r-- | fs/nfs/callback_proc.c | 57 |
1 files changed, 36 insertions, 21 deletions
diff --git a/fs/nfs/callback_proc.c b/fs/nfs/callback_proc.c index d4d1954e9bb9..74780f9f852c 100644 --- a/fs/nfs/callback_proc.c +++ b/fs/nfs/callback_proc.c | |||
@@ -111,6 +111,7 @@ int nfs4_validate_delegation_stateid(struct nfs_delegation *delegation, const nf | |||
111 | static u32 initiate_file_draining(struct nfs_client *clp, | 111 | static u32 initiate_file_draining(struct nfs_client *clp, |
112 | struct cb_layoutrecallargs *args) | 112 | struct cb_layoutrecallargs *args) |
113 | { | 113 | { |
114 | struct nfs_server *server; | ||
114 | struct pnfs_layout_hdr *lo; | 115 | struct pnfs_layout_hdr *lo; |
115 | struct inode *ino; | 116 | struct inode *ino; |
116 | bool found = false; | 117 | bool found = false; |
@@ -118,21 +119,28 @@ static u32 initiate_file_draining(struct nfs_client *clp, | |||
118 | LIST_HEAD(free_me_list); | 119 | LIST_HEAD(free_me_list); |
119 | 120 | ||
120 | spin_lock(&clp->cl_lock); | 121 | spin_lock(&clp->cl_lock); |
121 | list_for_each_entry(lo, &clp->cl_layouts, plh_layouts) { | 122 | rcu_read_lock(); |
122 | if (nfs_compare_fh(&args->cbl_fh, | 123 | list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link) { |
123 | &NFS_I(lo->plh_inode)->fh)) | 124 | list_for_each_entry(lo, &server->layouts, plh_layouts) { |
124 | continue; | 125 | if (nfs_compare_fh(&args->cbl_fh, |
125 | ino = igrab(lo->plh_inode); | 126 | &NFS_I(lo->plh_inode)->fh)) |
126 | if (!ino) | 127 | continue; |
127 | continue; | 128 | ino = igrab(lo->plh_inode); |
128 | found = true; | 129 | if (!ino) |
129 | /* Without this, layout can be freed as soon | 130 | continue; |
130 | * as we release cl_lock. | 131 | found = true; |
131 | */ | 132 | /* Without this, layout can be freed as soon |
132 | get_layout_hdr(lo); | 133 | * as we release cl_lock. |
133 | break; | 134 | */ |
135 | get_layout_hdr(lo); | ||
136 | break; | ||
137 | } | ||
138 | if (found) | ||
139 | break; | ||
134 | } | 140 | } |
141 | rcu_read_unlock(); | ||
135 | spin_unlock(&clp->cl_lock); | 142 | spin_unlock(&clp->cl_lock); |
143 | |||
136 | if (!found) | 144 | if (!found) |
137 | return NFS4ERR_NOMATCHING_LAYOUT; | 145 | return NFS4ERR_NOMATCHING_LAYOUT; |
138 | 146 | ||
@@ -154,6 +162,7 @@ static u32 initiate_file_draining(struct nfs_client *clp, | |||
154 | static u32 initiate_bulk_draining(struct nfs_client *clp, | 162 | static u32 initiate_bulk_draining(struct nfs_client *clp, |
155 | struct cb_layoutrecallargs *args) | 163 | struct cb_layoutrecallargs *args) |
156 | { | 164 | { |
165 | struct nfs_server *server; | ||
157 | struct pnfs_layout_hdr *lo; | 166 | struct pnfs_layout_hdr *lo; |
158 | struct inode *ino; | 167 | struct inode *ino; |
159 | u32 rv = NFS4ERR_NOMATCHING_LAYOUT; | 168 | u32 rv = NFS4ERR_NOMATCHING_LAYOUT; |
@@ -167,18 +176,24 @@ static u32 initiate_bulk_draining(struct nfs_client *clp, | |||
167 | }; | 176 | }; |
168 | 177 | ||
169 | spin_lock(&clp->cl_lock); | 178 | spin_lock(&clp->cl_lock); |
170 | list_for_each_entry(lo, &clp->cl_layouts, plh_layouts) { | 179 | rcu_read_lock(); |
180 | list_for_each_entry_rcu(server, &clp->cl_superblocks, client_link) { | ||
171 | if ((args->cbl_recall_type == RETURN_FSID) && | 181 | if ((args->cbl_recall_type == RETURN_FSID) && |
172 | memcmp(&NFS_SERVER(lo->plh_inode)->fsid, | 182 | memcmp(&server->fsid, &args->cbl_fsid, |
173 | &args->cbl_fsid, sizeof(struct nfs_fsid))) | 183 | sizeof(struct nfs_fsid))) |
174 | continue; | ||
175 | if (!igrab(lo->plh_inode)) | ||
176 | continue; | 184 | continue; |
177 | get_layout_hdr(lo); | 185 | |
178 | BUG_ON(!list_empty(&lo->plh_bulk_recall)); | 186 | list_for_each_entry(lo, &server->layouts, plh_layouts) { |
179 | list_add(&lo->plh_bulk_recall, &recall_list); | 187 | if (!igrab(lo->plh_inode)) |
188 | continue; | ||
189 | get_layout_hdr(lo); | ||
190 | BUG_ON(!list_empty(&lo->plh_bulk_recall)); | ||
191 | list_add(&lo->plh_bulk_recall, &recall_list); | ||
192 | } | ||
180 | } | 193 | } |
194 | rcu_read_unlock(); | ||
181 | spin_unlock(&clp->cl_lock); | 195 | spin_unlock(&clp->cl_lock); |
196 | |||
182 | list_for_each_entry_safe(lo, tmp, | 197 | list_for_each_entry_safe(lo, tmp, |
183 | &recall_list, plh_bulk_recall) { | 198 | &recall_list, plh_bulk_recall) { |
184 | ino = lo->plh_inode; | 199 | ino = lo->plh_inode; |