diff options
author | Bryan Schumaker <bjschuma@netapp.com> | 2012-01-27 10:22:49 -0500 |
---|---|---|
committer | J. Bruce Fields <bfields@redhat.com> | 2012-02-17 18:38:52 -0500 |
commit | 03cfb42025a16dc45195dbdd6d368daaa8367429 (patch) | |
tree | 5c1fbae03c905fb22b40f53d04e7616e413a0b3d /fs/nfsd | |
parent | de5b8e8e047534aac6bc9803f96e7257436aef9c (diff) |
NFSD: Clean up the test_stateid function
When I initially wrote it, I didn't understand how lists worked so I
wrote something that didn't use them. I think making a list of stateids
to test is a more straightforward implementation, especially compared to
especially compared to decoding stateids while simultaneously encoding
a reply to the client.
Signed-off-by: Bryan Schumaker <bjschuma@netapp.com>
Signed-off-by: J. Bruce Fields <bfields@redhat.com>
Diffstat (limited to 'fs/nfsd')
-rw-r--r-- | fs/nfsd/nfs4state.c | 9 | ||||
-rw-r--r-- | fs/nfsd/nfs4xdr.c | 66 | ||||
-rw-r--r-- | fs/nfsd/xdr4.h | 9 |
3 files changed, 35 insertions, 49 deletions
diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c index 45966a436b0a..f1b74a74ec49 100644 --- a/fs/nfsd/nfs4state.c +++ b/fs/nfsd/nfs4state.c | |||
@@ -3402,7 +3402,14 @@ __be32 | |||
3402 | nfsd4_test_stateid(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, | 3402 | nfsd4_test_stateid(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, |
3403 | struct nfsd4_test_stateid *test_stateid) | 3403 | struct nfsd4_test_stateid *test_stateid) |
3404 | { | 3404 | { |
3405 | /* real work is done during encoding */ | 3405 | struct nfsd4_test_stateid_id *stateid; |
3406 | struct nfs4_client *cl = cstate->session->se_client; | ||
3407 | |||
3408 | nfs4_lock_state(); | ||
3409 | list_for_each_entry(stateid, &test_stateid->ts_stateid_list, ts_id_list) | ||
3410 | stateid->ts_id_status = nfs4_validate_stateid(cl, &stateid->ts_id_stateid); | ||
3411 | nfs4_unlock_state(); | ||
3412 | |||
3406 | return nfs_ok; | 3413 | return nfs_ok; |
3407 | } | 3414 | } |
3408 | 3415 | ||
diff --git a/fs/nfsd/nfs4xdr.c b/fs/nfsd/nfs4xdr.c index d241a8571ddf..a58f2064f479 100644 --- a/fs/nfsd/nfs4xdr.c +++ b/fs/nfsd/nfs4xdr.c | |||
@@ -133,22 +133,6 @@ xdr_error: \ | |||
133 | } \ | 133 | } \ |
134 | } while (0) | 134 | } while (0) |
135 | 135 | ||
136 | static void save_buf(struct nfsd4_compoundargs *argp, struct nfsd4_saved_compoundargs *savep) | ||
137 | { | ||
138 | savep->p = argp->p; | ||
139 | savep->end = argp->end; | ||
140 | savep->pagelen = argp->pagelen; | ||
141 | savep->pagelist = argp->pagelist; | ||
142 | } | ||
143 | |||
144 | static void restore_buf(struct nfsd4_compoundargs *argp, struct nfsd4_saved_compoundargs *savep) | ||
145 | { | ||
146 | argp->p = savep->p; | ||
147 | argp->end = savep->end; | ||
148 | argp->pagelen = savep->pagelen; | ||
149 | argp->pagelist = savep->pagelist; | ||
150 | } | ||
151 | |||
152 | static __be32 *read_buf(struct nfsd4_compoundargs *argp, u32 nbytes) | 136 | static __be32 *read_buf(struct nfsd4_compoundargs *argp, u32 nbytes) |
153 | { | 137 | { |
154 | /* We want more bytes than seem to be available. | 138 | /* We want more bytes than seem to be available. |
@@ -1396,26 +1380,29 @@ nfsd4_decode_sequence(struct nfsd4_compoundargs *argp, | |||
1396 | static __be32 | 1380 | static __be32 |
1397 | nfsd4_decode_test_stateid(struct nfsd4_compoundargs *argp, struct nfsd4_test_stateid *test_stateid) | 1381 | nfsd4_decode_test_stateid(struct nfsd4_compoundargs *argp, struct nfsd4_test_stateid *test_stateid) |
1398 | { | 1382 | { |
1399 | unsigned int nbytes; | ||
1400 | stateid_t si; | ||
1401 | int i; | 1383 | int i; |
1402 | __be32 *p; | 1384 | __be32 *p, status; |
1403 | __be32 status; | 1385 | struct nfsd4_test_stateid_id *stateid; |
1404 | 1386 | ||
1405 | READ_BUF(4); | 1387 | READ_BUF(4); |
1406 | test_stateid->ts_num_ids = ntohl(*p++); | 1388 | test_stateid->ts_num_ids = ntohl(*p++); |
1407 | 1389 | ||
1408 | nbytes = test_stateid->ts_num_ids * sizeof(stateid_t); | 1390 | INIT_LIST_HEAD(&test_stateid->ts_stateid_list); |
1409 | if (nbytes > (u32)((char *)argp->end - (char *)argp->p)) | ||
1410 | goto xdr_error; | ||
1411 | |||
1412 | test_stateid->ts_saved_args = argp; | ||
1413 | save_buf(argp, &test_stateid->ts_savedp); | ||
1414 | 1391 | ||
1415 | for (i = 0; i < test_stateid->ts_num_ids; i++) { | 1392 | for (i = 0; i < test_stateid->ts_num_ids; i++) { |
1416 | status = nfsd4_decode_stateid(argp, &si); | 1393 | stateid = kmalloc(sizeof(struct nfsd4_test_stateid_id), GFP_KERNEL); |
1394 | if (!stateid) { | ||
1395 | status = PTR_ERR(stateid); | ||
1396 | goto out; | ||
1397 | } | ||
1398 | |||
1399 | defer_free(argp, kfree, stateid); | ||
1400 | INIT_LIST_HEAD(&stateid->ts_id_list); | ||
1401 | list_add_tail(&stateid->ts_id_list, &test_stateid->ts_stateid_list); | ||
1402 | |||
1403 | status = nfsd4_decode_stateid(argp, &stateid->ts_id_stateid); | ||
1417 | if (status) | 1404 | if (status) |
1418 | return status; | 1405 | goto out; |
1419 | } | 1406 | } |
1420 | 1407 | ||
1421 | status = 0; | 1408 | status = 0; |
@@ -3402,30 +3389,17 @@ __be32 | |||
3402 | nfsd4_encode_test_stateid(struct nfsd4_compoundres *resp, int nfserr, | 3389 | nfsd4_encode_test_stateid(struct nfsd4_compoundres *resp, int nfserr, |
3403 | struct nfsd4_test_stateid *test_stateid) | 3390 | struct nfsd4_test_stateid *test_stateid) |
3404 | { | 3391 | { |
3405 | struct nfsd4_compoundargs *argp; | 3392 | struct nfsd4_test_stateid_id *stateid, *next; |
3406 | struct nfs4_client *cl = resp->cstate.session->se_client; | ||
3407 | stateid_t si; | ||
3408 | __be32 *p; | 3393 | __be32 *p; |
3409 | int i; | ||
3410 | int valid; | ||
3411 | 3394 | ||
3412 | restore_buf(test_stateid->ts_saved_args, &test_stateid->ts_savedp); | 3395 | RESERVE_SPACE(4 + (4 * test_stateid->ts_num_ids)); |
3413 | argp = test_stateid->ts_saved_args; | ||
3414 | |||
3415 | RESERVE_SPACE(4); | ||
3416 | *p++ = htonl(test_stateid->ts_num_ids); | 3396 | *p++ = htonl(test_stateid->ts_num_ids); |
3417 | resp->p = p; | ||
3418 | 3397 | ||
3419 | nfs4_lock_state(); | 3398 | list_for_each_entry_safe(stateid, next, &test_stateid->ts_stateid_list, ts_id_list) { |
3420 | for (i = 0; i < test_stateid->ts_num_ids; i++) { | 3399 | *p++ = htonl(stateid->ts_id_status); |
3421 | nfsd4_decode_stateid(argp, &si); | ||
3422 | valid = nfs4_validate_stateid(cl, &si); | ||
3423 | RESERVE_SPACE(4); | ||
3424 | *p++ = htonl(valid); | ||
3425 | resp->p = p; | ||
3426 | } | 3400 | } |
3427 | nfs4_unlock_state(); | ||
3428 | 3401 | ||
3402 | ADJUST_ARGS(); | ||
3429 | return nfserr; | 3403 | return nfserr; |
3430 | } | 3404 | } |
3431 | 3405 | ||
diff --git a/fs/nfsd/xdr4.h b/fs/nfsd/xdr4.h index 4949832fd74a..7110a082275f 100644 --- a/fs/nfsd/xdr4.h +++ b/fs/nfsd/xdr4.h | |||
@@ -356,10 +356,15 @@ struct nfsd4_saved_compoundargs { | |||
356 | struct page **pagelist; | 356 | struct page **pagelist; |
357 | }; | 357 | }; |
358 | 358 | ||
359 | struct nfsd4_test_stateid_id { | ||
360 | __be32 ts_id_status; | ||
361 | stateid_t ts_id_stateid; | ||
362 | struct list_head ts_id_list; | ||
363 | }; | ||
364 | |||
359 | struct nfsd4_test_stateid { | 365 | struct nfsd4_test_stateid { |
360 | __be32 ts_num_ids; | 366 | __be32 ts_num_ids; |
361 | struct nfsd4_compoundargs *ts_saved_args; | 367 | struct list_head ts_stateid_list; |
362 | struct nfsd4_saved_compoundargs ts_savedp; | ||
363 | }; | 368 | }; |
364 | 369 | ||
365 | struct nfsd4_free_stateid { | 370 | struct nfsd4_free_stateid { |