xref: /openbmc/linux/fs/afs/fsclient.c (revision 256ac037)
1 /* AFS File Server client stubs
2  *
3  * Copyright (C) 2002, 2007 Red Hat, Inc. All Rights Reserved.
4  * Written by David Howells (dhowells@redhat.com)
5  *
6  * This program is free software; you can redistribute it and/or
7  * modify it under the terms of the GNU General Public License
8  * as published by the Free Software Foundation; either version
9  * 2 of the License, or (at your option) any later version.
10  */
11 
12 #include <linux/init.h>
13 #include <linux/slab.h>
14 #include <linux/sched.h>
15 #include <linux/circ_buf.h>
16 #include "internal.h"
17 #include "afs_fs.h"
18 
19 /*
20  * We need somewhere to discard into in case the server helpfully returns more
21  * than we asked for in FS.FetchData{,64}.
22  */
23 static u8 afs_discard_buffer[64];
24 
25 /*
26  * decode an AFSFid block
27  */
28 static void xdr_decode_AFSFid(const __be32 **_bp, struct afs_fid *fid)
29 {
30 	const __be32 *bp = *_bp;
31 
32 	fid->vid		= ntohl(*bp++);
33 	fid->vnode		= ntohl(*bp++);
34 	fid->unique		= ntohl(*bp++);
35 	*_bp = bp;
36 }
37 
38 /*
39  * decode an AFSFetchStatus block
40  */
41 static void xdr_decode_AFSFetchStatus(const __be32 **_bp,
42 				      struct afs_file_status *status,
43 				      struct afs_vnode *vnode,
44 				      afs_dataversion_t *store_version)
45 {
46 	afs_dataversion_t expected_version;
47 	const __be32 *bp = *_bp;
48 	umode_t mode;
49 	u64 data_version, size;
50 	u32 changed = 0; /* becomes non-zero if ctime-type changes seen */
51 	kuid_t owner;
52 	kgid_t group;
53 
54 #define EXTRACT(DST)				\
55 	do {					\
56 		u32 x = ntohl(*bp++);		\
57 		changed |= DST - x;		\
58 		DST = x;			\
59 	} while (0)
60 
61 	status->if_version = ntohl(*bp++);
62 	EXTRACT(status->type);
63 	EXTRACT(status->nlink);
64 	size = ntohl(*bp++);
65 	data_version = ntohl(*bp++);
66 	EXTRACT(status->author);
67 	owner = make_kuid(&init_user_ns, ntohl(*bp++));
68 	changed |= !uid_eq(owner, status->owner);
69 	status->owner = owner;
70 	EXTRACT(status->caller_access); /* call ticket dependent */
71 	EXTRACT(status->anon_access);
72 	EXTRACT(status->mode);
73 	EXTRACT(status->parent.vnode);
74 	EXTRACT(status->parent.unique);
75 	bp++; /* seg size */
76 	status->mtime_client = ntohl(*bp++);
77 	status->mtime_server = ntohl(*bp++);
78 	group = make_kgid(&init_user_ns, ntohl(*bp++));
79 	changed |= !gid_eq(group, status->group);
80 	status->group = group;
81 	bp++; /* sync counter */
82 	data_version |= (u64) ntohl(*bp++) << 32;
83 	EXTRACT(status->lock_count);
84 	size |= (u64) ntohl(*bp++) << 32;
85 	bp++; /* spare 4 */
86 	*_bp = bp;
87 
88 	if (size != status->size) {
89 		status->size = size;
90 		changed |= true;
91 	}
92 	status->mode &= S_IALLUGO;
93 
94 	_debug("vnode time %lx, %lx",
95 	       status->mtime_client, status->mtime_server);
96 
97 	if (vnode) {
98 		status->parent.vid = vnode->fid.vid;
99 		if (changed && !test_bit(AFS_VNODE_UNSET, &vnode->flags)) {
100 			_debug("vnode changed");
101 			i_size_write(&vnode->vfs_inode, size);
102 			vnode->vfs_inode.i_uid = status->owner;
103 			vnode->vfs_inode.i_gid = status->group;
104 			vnode->vfs_inode.i_generation = vnode->fid.unique;
105 			set_nlink(&vnode->vfs_inode, status->nlink);
106 
107 			mode = vnode->vfs_inode.i_mode;
108 			mode &= ~S_IALLUGO;
109 			mode |= status->mode;
110 			barrier();
111 			vnode->vfs_inode.i_mode = mode;
112 		}
113 
114 		vnode->vfs_inode.i_ctime.tv_sec	= status->mtime_client;
115 		vnode->vfs_inode.i_mtime	= vnode->vfs_inode.i_ctime;
116 		vnode->vfs_inode.i_atime	= vnode->vfs_inode.i_ctime;
117 		vnode->vfs_inode.i_version	= data_version;
118 	}
119 
120 	expected_version = status->data_version;
121 	if (store_version)
122 		expected_version = *store_version;
123 
124 	if (expected_version != data_version) {
125 		status->data_version = data_version;
126 		if (vnode && !test_bit(AFS_VNODE_UNSET, &vnode->flags)) {
127 			_debug("vnode modified %llx on {%x:%u}",
128 			       (unsigned long long) data_version,
129 			       vnode->fid.vid, vnode->fid.vnode);
130 			set_bit(AFS_VNODE_MODIFIED, &vnode->flags);
131 			set_bit(AFS_VNODE_ZAP_DATA, &vnode->flags);
132 		}
133 	} else if (store_version) {
134 		status->data_version = data_version;
135 	}
136 }
137 
138 /*
139  * decode an AFSCallBack block
140  */
141 static void xdr_decode_AFSCallBack(const __be32 **_bp, struct afs_vnode *vnode)
142 {
143 	const __be32 *bp = *_bp;
144 
145 	vnode->cb_version	= ntohl(*bp++);
146 	vnode->cb_expiry	= ntohl(*bp++);
147 	vnode->cb_type		= ntohl(*bp++);
148 	vnode->cb_expires	= vnode->cb_expiry + ktime_get_real_seconds();
149 	*_bp = bp;
150 }
151 
152 static void xdr_decode_AFSCallBack_raw(const __be32 **_bp,
153 				       struct afs_callback *cb)
154 {
155 	const __be32 *bp = *_bp;
156 
157 	cb->version	= ntohl(*bp++);
158 	cb->expiry	= ntohl(*bp++);
159 	cb->type	= ntohl(*bp++);
160 	*_bp = bp;
161 }
162 
163 /*
164  * decode an AFSVolSync block
165  */
166 static void xdr_decode_AFSVolSync(const __be32 **_bp,
167 				  struct afs_volsync *volsync)
168 {
169 	const __be32 *bp = *_bp;
170 
171 	volsync->creation = ntohl(*bp++);
172 	bp++; /* spare2 */
173 	bp++; /* spare3 */
174 	bp++; /* spare4 */
175 	bp++; /* spare5 */
176 	bp++; /* spare6 */
177 	*_bp = bp;
178 }
179 
180 /*
181  * encode the requested attributes into an AFSStoreStatus block
182  */
183 static void xdr_encode_AFS_StoreStatus(__be32 **_bp, struct iattr *attr)
184 {
185 	__be32 *bp = *_bp;
186 	u32 mask = 0, mtime = 0, owner = 0, group = 0, mode = 0;
187 
188 	mask = 0;
189 	if (attr->ia_valid & ATTR_MTIME) {
190 		mask |= AFS_SET_MTIME;
191 		mtime = attr->ia_mtime.tv_sec;
192 	}
193 
194 	if (attr->ia_valid & ATTR_UID) {
195 		mask |= AFS_SET_OWNER;
196 		owner = from_kuid(&init_user_ns, attr->ia_uid);
197 	}
198 
199 	if (attr->ia_valid & ATTR_GID) {
200 		mask |= AFS_SET_GROUP;
201 		group = from_kgid(&init_user_ns, attr->ia_gid);
202 	}
203 
204 	if (attr->ia_valid & ATTR_MODE) {
205 		mask |= AFS_SET_MODE;
206 		mode = attr->ia_mode & S_IALLUGO;
207 	}
208 
209 	*bp++ = htonl(mask);
210 	*bp++ = htonl(mtime);
211 	*bp++ = htonl(owner);
212 	*bp++ = htonl(group);
213 	*bp++ = htonl(mode);
214 	*bp++ = 0;		/* segment size */
215 	*_bp = bp;
216 }
217 
218 /*
219  * decode an AFSFetchVolumeStatus block
220  */
221 static void xdr_decode_AFSFetchVolumeStatus(const __be32 **_bp,
222 					    struct afs_volume_status *vs)
223 {
224 	const __be32 *bp = *_bp;
225 
226 	vs->vid			= ntohl(*bp++);
227 	vs->parent_id		= ntohl(*bp++);
228 	vs->online		= ntohl(*bp++);
229 	vs->in_service		= ntohl(*bp++);
230 	vs->blessed		= ntohl(*bp++);
231 	vs->needs_salvage	= ntohl(*bp++);
232 	vs->type		= ntohl(*bp++);
233 	vs->min_quota		= ntohl(*bp++);
234 	vs->max_quota		= ntohl(*bp++);
235 	vs->blocks_in_use	= ntohl(*bp++);
236 	vs->part_blocks_avail	= ntohl(*bp++);
237 	vs->part_max_blocks	= ntohl(*bp++);
238 	*_bp = bp;
239 }
240 
241 /*
242  * deliver reply data to an FS.FetchStatus
243  */
244 static int afs_deliver_fs_fetch_status(struct afs_call *call)
245 {
246 	struct afs_vnode *vnode = call->reply;
247 	const __be32 *bp;
248 	int ret;
249 
250 	_enter("");
251 
252 	ret = afs_transfer_reply(call);
253 	if (ret < 0)
254 		return ret;
255 
256 	/* unmarshall the reply once we've received all of it */
257 	bp = call->buffer;
258 	xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode, NULL);
259 	xdr_decode_AFSCallBack(&bp, vnode);
260 	if (call->reply2)
261 		xdr_decode_AFSVolSync(&bp, call->reply2);
262 
263 	_leave(" = 0 [done]");
264 	return 0;
265 }
266 
267 /*
268  * FS.FetchStatus operation type
269  */
270 static const struct afs_call_type afs_RXFSFetchStatus = {
271 	.name		= "FS.FetchStatus",
272 	.deliver	= afs_deliver_fs_fetch_status,
273 	.abort_to_error	= afs_abort_to_error,
274 	.destructor	= afs_flat_call_destructor,
275 };
276 
277 /*
278  * fetch the status information for a file
279  */
280 int afs_fs_fetch_file_status(struct afs_server *server,
281 			     struct key *key,
282 			     struct afs_vnode *vnode,
283 			     struct afs_volsync *volsync,
284 			     bool async)
285 {
286 	struct afs_call *call;
287 	__be32 *bp;
288 
289 	_enter(",%x,{%x:%u},,",
290 	       key_serial(key), vnode->fid.vid, vnode->fid.vnode);
291 
292 	call = afs_alloc_flat_call(&afs_RXFSFetchStatus, 16, (21 + 3 + 6) * 4);
293 	if (!call)
294 		return -ENOMEM;
295 
296 	call->key = key;
297 	call->reply = vnode;
298 	call->reply2 = volsync;
299 	call->service_id = FS_SERVICE;
300 	call->port = htons(AFS_FS_PORT);
301 
302 	/* marshall the parameters */
303 	bp = call->request;
304 	bp[0] = htonl(FSFETCHSTATUS);
305 	bp[1] = htonl(vnode->fid.vid);
306 	bp[2] = htonl(vnode->fid.vnode);
307 	bp[3] = htonl(vnode->fid.unique);
308 
309 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
310 }
311 
312 /*
313  * deliver reply data to an FS.FetchData
314  */
315 static int afs_deliver_fs_fetch_data(struct afs_call *call)
316 {
317 	struct afs_vnode *vnode = call->reply;
318 	struct afs_read *req = call->reply3;
319 	const __be32 *bp;
320 	unsigned int size;
321 	void *buffer;
322 	int ret;
323 
324 	_enter("{%u,%zu/%u;%llu/%llu}",
325 	       call->unmarshall, call->offset, call->count,
326 	       req->remain, req->actual_len);
327 
328 	switch (call->unmarshall) {
329 	case 0:
330 		req->actual_len = 0;
331 		call->offset = 0;
332 		call->unmarshall++;
333 		if (call->operation_ID != FSFETCHDATA64) {
334 			call->unmarshall++;
335 			goto no_msw;
336 		}
337 
338 		/* extract the upper part of the returned data length of an
339 		 * FSFETCHDATA64 op (which should always be 0 using this
340 		 * client) */
341 	case 1:
342 		_debug("extract data length (MSW)");
343 		ret = afs_extract_data(call, &call->tmp, 4, true);
344 		if (ret < 0)
345 			return ret;
346 
347 		req->actual_len = ntohl(call->tmp);
348 		req->actual_len <<= 32;
349 		call->offset = 0;
350 		call->unmarshall++;
351 
352 	no_msw:
353 		/* extract the returned data length */
354 	case 2:
355 		_debug("extract data length");
356 		ret = afs_extract_data(call, &call->tmp, 4, true);
357 		if (ret < 0)
358 			return ret;
359 
360 		req->actual_len |= ntohl(call->tmp);
361 		_debug("DATA length: %llu", req->actual_len);
362 
363 		req->remain = req->actual_len;
364 		call->offset = req->pos & (PAGE_SIZE - 1);
365 		req->index = 0;
366 		if (req->actual_len == 0)
367 			goto no_more_data;
368 		call->unmarshall++;
369 
370 	begin_page:
371 		ASSERTCMP(req->index, <, req->nr_pages);
372 		if (req->remain > PAGE_SIZE - call->offset)
373 			size = PAGE_SIZE - call->offset;
374 		else
375 			size = req->remain;
376 		call->count = call->offset + size;
377 		ASSERTCMP(call->count, <=, PAGE_SIZE);
378 		req->remain -= size;
379 
380 		/* extract the returned data */
381 	case 3:
382 		_debug("extract data %llu/%llu %zu/%u",
383 		       req->remain, req->actual_len, call->offset, call->count);
384 
385 		buffer = kmap(req->pages[req->index]);
386 		ret = afs_extract_data(call, buffer, call->count, true);
387 		kunmap(req->pages[req->index]);
388 		if (ret < 0)
389 			return ret;
390 		if (call->offset == PAGE_SIZE) {
391 			if (req->page_done)
392 				req->page_done(call, req);
393 			req->index++;
394 			if (req->remain > 0) {
395 				call->offset = 0;
396 				if (req->index >= req->nr_pages) {
397 					call->unmarshall = 4;
398 					goto begin_discard;
399 				}
400 				goto begin_page;
401 			}
402 		}
403 		goto no_more_data;
404 
405 		/* Discard any excess data the server gave us */
406 	begin_discard:
407 	case 4:
408 		size = min_t(loff_t, sizeof(afs_discard_buffer), req->remain);
409 		call->count = size;
410 		_debug("extract discard %llu/%llu %zu/%u",
411 		       req->remain, req->actual_len, call->offset, call->count);
412 
413 		call->offset = 0;
414 		ret = afs_extract_data(call, afs_discard_buffer, call->count, true);
415 		req->remain -= call->offset;
416 		if (ret < 0)
417 			return ret;
418 		if (req->remain > 0)
419 			goto begin_discard;
420 
421 	no_more_data:
422 		call->offset = 0;
423 		call->unmarshall = 5;
424 
425 		/* extract the metadata */
426 	case 5:
427 		ret = afs_extract_data(call, call->buffer,
428 				       (21 + 3 + 6) * 4, false);
429 		if (ret < 0)
430 			return ret;
431 
432 		bp = call->buffer;
433 		xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode, NULL);
434 		xdr_decode_AFSCallBack(&bp, vnode);
435 		if (call->reply2)
436 			xdr_decode_AFSVolSync(&bp, call->reply2);
437 
438 		call->offset = 0;
439 		call->unmarshall++;
440 
441 	case 6:
442 		break;
443 	}
444 
445 	for (; req->index < req->nr_pages; req->index++) {
446 		if (call->count < PAGE_SIZE)
447 			zero_user_segment(req->pages[req->index],
448 					  call->count, PAGE_SIZE);
449 		if (req->page_done)
450 			req->page_done(call, req);
451 		call->count = 0;
452 	}
453 
454 	_leave(" = 0 [done]");
455 	return 0;
456 }
457 
458 static void afs_fetch_data_destructor(struct afs_call *call)
459 {
460 	struct afs_read *req = call->reply3;
461 
462 	afs_put_read(req);
463 	afs_flat_call_destructor(call);
464 }
465 
466 /*
467  * FS.FetchData operation type
468  */
469 static const struct afs_call_type afs_RXFSFetchData = {
470 	.name		= "FS.FetchData",
471 	.deliver	= afs_deliver_fs_fetch_data,
472 	.abort_to_error	= afs_abort_to_error,
473 	.destructor	= afs_fetch_data_destructor,
474 };
475 
476 static const struct afs_call_type afs_RXFSFetchData64 = {
477 	.name		= "FS.FetchData64",
478 	.deliver	= afs_deliver_fs_fetch_data,
479 	.abort_to_error	= afs_abort_to_error,
480 	.destructor	= afs_fetch_data_destructor,
481 };
482 
483 /*
484  * fetch data from a very large file
485  */
486 static int afs_fs_fetch_data64(struct afs_server *server,
487 			       struct key *key,
488 			       struct afs_vnode *vnode,
489 			       struct afs_read *req,
490 			       bool async)
491 {
492 	struct afs_call *call;
493 	__be32 *bp;
494 
495 	_enter("");
496 
497 	call = afs_alloc_flat_call(&afs_RXFSFetchData64, 32, (21 + 3 + 6) * 4);
498 	if (!call)
499 		return -ENOMEM;
500 
501 	call->key = key;
502 	call->reply = vnode;
503 	call->reply2 = NULL; /* volsync */
504 	call->reply3 = req;
505 	call->service_id = FS_SERVICE;
506 	call->port = htons(AFS_FS_PORT);
507 	call->operation_ID = FSFETCHDATA64;
508 
509 	/* marshall the parameters */
510 	bp = call->request;
511 	bp[0] = htonl(FSFETCHDATA64);
512 	bp[1] = htonl(vnode->fid.vid);
513 	bp[2] = htonl(vnode->fid.vnode);
514 	bp[3] = htonl(vnode->fid.unique);
515 	bp[4] = htonl(upper_32_bits(req->pos));
516 	bp[5] = htonl(lower_32_bits(req->pos));
517 	bp[6] = 0;
518 	bp[7] = htonl(lower_32_bits(req->len));
519 
520 	atomic_inc(&req->usage);
521 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
522 }
523 
524 /*
525  * fetch data from a file
526  */
527 int afs_fs_fetch_data(struct afs_server *server,
528 		      struct key *key,
529 		      struct afs_vnode *vnode,
530 		      struct afs_read *req,
531 		      bool async)
532 {
533 	struct afs_call *call;
534 	__be32 *bp;
535 
536 	if (upper_32_bits(req->pos) ||
537 	    upper_32_bits(req->len) ||
538 	    upper_32_bits(req->pos + req->len))
539 		return afs_fs_fetch_data64(server, key, vnode, req, async);
540 
541 	_enter("");
542 
543 	call = afs_alloc_flat_call(&afs_RXFSFetchData, 24, (21 + 3 + 6) * 4);
544 	if (!call)
545 		return -ENOMEM;
546 
547 	call->key = key;
548 	call->reply = vnode;
549 	call->reply2 = NULL; /* volsync */
550 	call->reply3 = req;
551 	call->service_id = FS_SERVICE;
552 	call->port = htons(AFS_FS_PORT);
553 	call->operation_ID = FSFETCHDATA;
554 
555 	/* marshall the parameters */
556 	bp = call->request;
557 	bp[0] = htonl(FSFETCHDATA);
558 	bp[1] = htonl(vnode->fid.vid);
559 	bp[2] = htonl(vnode->fid.vnode);
560 	bp[3] = htonl(vnode->fid.unique);
561 	bp[4] = htonl(lower_32_bits(req->pos));
562 	bp[5] = htonl(lower_32_bits(req->len));
563 
564 	atomic_inc(&req->usage);
565 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
566 }
567 
568 /*
569  * deliver reply data to an FS.GiveUpCallBacks
570  */
571 static int afs_deliver_fs_give_up_callbacks(struct afs_call *call)
572 {
573 	_enter("");
574 
575 	/* shouldn't be any reply data */
576 	return afs_extract_data(call, NULL, 0, false);
577 }
578 
579 /*
580  * FS.GiveUpCallBacks operation type
581  */
582 static const struct afs_call_type afs_RXFSGiveUpCallBacks = {
583 	.name		= "FS.GiveUpCallBacks",
584 	.deliver	= afs_deliver_fs_give_up_callbacks,
585 	.abort_to_error	= afs_abort_to_error,
586 	.destructor	= afs_flat_call_destructor,
587 };
588 
589 /*
590  * give up a set of callbacks
591  * - the callbacks are held in the server->cb_break ring
592  */
593 int afs_fs_give_up_callbacks(struct afs_server *server,
594 			     bool async)
595 {
596 	struct afs_call *call;
597 	size_t ncallbacks;
598 	__be32 *bp, *tp;
599 	int loop;
600 
601 	ncallbacks = CIRC_CNT(server->cb_break_head, server->cb_break_tail,
602 			      ARRAY_SIZE(server->cb_break));
603 
604 	_enter("{%zu},", ncallbacks);
605 
606 	if (ncallbacks == 0)
607 		return 0;
608 	if (ncallbacks > AFSCBMAX)
609 		ncallbacks = AFSCBMAX;
610 
611 	_debug("break %zu callbacks", ncallbacks);
612 
613 	call = afs_alloc_flat_call(&afs_RXFSGiveUpCallBacks,
614 				   12 + ncallbacks * 6 * 4, 0);
615 	if (!call)
616 		return -ENOMEM;
617 
618 	call->service_id = FS_SERVICE;
619 	call->port = htons(AFS_FS_PORT);
620 
621 	/* marshall the parameters */
622 	bp = call->request;
623 	tp = bp + 2 + ncallbacks * 3;
624 	*bp++ = htonl(FSGIVEUPCALLBACKS);
625 	*bp++ = htonl(ncallbacks);
626 	*tp++ = htonl(ncallbacks);
627 
628 	atomic_sub(ncallbacks, &server->cb_break_n);
629 	for (loop = ncallbacks; loop > 0; loop--) {
630 		struct afs_callback *cb =
631 			&server->cb_break[server->cb_break_tail];
632 
633 		*bp++ = htonl(cb->fid.vid);
634 		*bp++ = htonl(cb->fid.vnode);
635 		*bp++ = htonl(cb->fid.unique);
636 		*tp++ = htonl(cb->version);
637 		*tp++ = htonl(cb->expiry);
638 		*tp++ = htonl(cb->type);
639 		smp_mb();
640 		server->cb_break_tail =
641 			(server->cb_break_tail + 1) &
642 			(ARRAY_SIZE(server->cb_break) - 1);
643 	}
644 
645 	ASSERT(ncallbacks > 0);
646 	wake_up_nr(&server->cb_break_waitq, ncallbacks);
647 
648 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
649 }
650 
651 /*
652  * deliver reply data to an FS.CreateFile or an FS.MakeDir
653  */
654 static int afs_deliver_fs_create_vnode(struct afs_call *call)
655 {
656 	struct afs_vnode *vnode = call->reply;
657 	const __be32 *bp;
658 	int ret;
659 
660 	_enter("{%u}", call->unmarshall);
661 
662 	ret = afs_transfer_reply(call);
663 	if (ret < 0)
664 		return ret;
665 
666 	/* unmarshall the reply once we've received all of it */
667 	bp = call->buffer;
668 	xdr_decode_AFSFid(&bp, call->reply2);
669 	xdr_decode_AFSFetchStatus(&bp, call->reply3, NULL, NULL);
670 	xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode, NULL);
671 	xdr_decode_AFSCallBack_raw(&bp, call->reply4);
672 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
673 
674 	_leave(" = 0 [done]");
675 	return 0;
676 }
677 
678 /*
679  * FS.CreateFile and FS.MakeDir operation type
680  */
681 static const struct afs_call_type afs_RXFSCreateXXXX = {
682 	.name		= "FS.CreateXXXX",
683 	.deliver	= afs_deliver_fs_create_vnode,
684 	.abort_to_error	= afs_abort_to_error,
685 	.destructor	= afs_flat_call_destructor,
686 };
687 
688 /*
689  * create a file or make a directory
690  */
691 int afs_fs_create(struct afs_server *server,
692 		  struct key *key,
693 		  struct afs_vnode *vnode,
694 		  const char *name,
695 		  umode_t mode,
696 		  struct afs_fid *newfid,
697 		  struct afs_file_status *newstatus,
698 		  struct afs_callback *newcb,
699 		  bool async)
700 {
701 	struct afs_call *call;
702 	size_t namesz, reqsz, padsz;
703 	__be32 *bp;
704 
705 	_enter("");
706 
707 	namesz = strlen(name);
708 	padsz = (4 - (namesz & 3)) & 3;
709 	reqsz = (5 * 4) + namesz + padsz + (6 * 4);
710 
711 	call = afs_alloc_flat_call(&afs_RXFSCreateXXXX, reqsz,
712 				   (3 + 21 + 21 + 3 + 6) * 4);
713 	if (!call)
714 		return -ENOMEM;
715 
716 	call->key = key;
717 	call->reply = vnode;
718 	call->reply2 = newfid;
719 	call->reply3 = newstatus;
720 	call->reply4 = newcb;
721 	call->service_id = FS_SERVICE;
722 	call->port = htons(AFS_FS_PORT);
723 
724 	/* marshall the parameters */
725 	bp = call->request;
726 	*bp++ = htonl(S_ISDIR(mode) ? FSMAKEDIR : FSCREATEFILE);
727 	*bp++ = htonl(vnode->fid.vid);
728 	*bp++ = htonl(vnode->fid.vnode);
729 	*bp++ = htonl(vnode->fid.unique);
730 	*bp++ = htonl(namesz);
731 	memcpy(bp, name, namesz);
732 	bp = (void *) bp + namesz;
733 	if (padsz > 0) {
734 		memset(bp, 0, padsz);
735 		bp = (void *) bp + padsz;
736 	}
737 	*bp++ = htonl(AFS_SET_MODE | AFS_SET_MTIME);
738 	*bp++ = htonl(vnode->vfs_inode.i_mtime.tv_sec); /* mtime */
739 	*bp++ = 0; /* owner */
740 	*bp++ = 0; /* group */
741 	*bp++ = htonl(mode & S_IALLUGO); /* unix mode */
742 	*bp++ = 0; /* segment size */
743 
744 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
745 }
746 
747 /*
748  * deliver reply data to an FS.RemoveFile or FS.RemoveDir
749  */
750 static int afs_deliver_fs_remove(struct afs_call *call)
751 {
752 	struct afs_vnode *vnode = call->reply;
753 	const __be32 *bp;
754 	int ret;
755 
756 	_enter("{%u}", call->unmarshall);
757 
758 	ret = afs_transfer_reply(call);
759 	if (ret < 0)
760 		return ret;
761 
762 	/* unmarshall the reply once we've received all of it */
763 	bp = call->buffer;
764 	xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode, NULL);
765 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
766 
767 	_leave(" = 0 [done]");
768 	return 0;
769 }
770 
771 /*
772  * FS.RemoveDir/FS.RemoveFile operation type
773  */
774 static const struct afs_call_type afs_RXFSRemoveXXXX = {
775 	.name		= "FS.RemoveXXXX",
776 	.deliver	= afs_deliver_fs_remove,
777 	.abort_to_error	= afs_abort_to_error,
778 	.destructor	= afs_flat_call_destructor,
779 };
780 
781 /*
782  * remove a file or directory
783  */
784 int afs_fs_remove(struct afs_server *server,
785 		  struct key *key,
786 		  struct afs_vnode *vnode,
787 		  const char *name,
788 		  bool isdir,
789 		  bool async)
790 {
791 	struct afs_call *call;
792 	size_t namesz, reqsz, padsz;
793 	__be32 *bp;
794 
795 	_enter("");
796 
797 	namesz = strlen(name);
798 	padsz = (4 - (namesz & 3)) & 3;
799 	reqsz = (5 * 4) + namesz + padsz;
800 
801 	call = afs_alloc_flat_call(&afs_RXFSRemoveXXXX, reqsz, (21 + 6) * 4);
802 	if (!call)
803 		return -ENOMEM;
804 
805 	call->key = key;
806 	call->reply = vnode;
807 	call->service_id = FS_SERVICE;
808 	call->port = htons(AFS_FS_PORT);
809 
810 	/* marshall the parameters */
811 	bp = call->request;
812 	*bp++ = htonl(isdir ? FSREMOVEDIR : FSREMOVEFILE);
813 	*bp++ = htonl(vnode->fid.vid);
814 	*bp++ = htonl(vnode->fid.vnode);
815 	*bp++ = htonl(vnode->fid.unique);
816 	*bp++ = htonl(namesz);
817 	memcpy(bp, name, namesz);
818 	bp = (void *) bp + namesz;
819 	if (padsz > 0) {
820 		memset(bp, 0, padsz);
821 		bp = (void *) bp + padsz;
822 	}
823 
824 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
825 }
826 
827 /*
828  * deliver reply data to an FS.Link
829  */
830 static int afs_deliver_fs_link(struct afs_call *call)
831 {
832 	struct afs_vnode *dvnode = call->reply, *vnode = call->reply2;
833 	const __be32 *bp;
834 	int ret;
835 
836 	_enter("{%u}", call->unmarshall);
837 
838 	ret = afs_transfer_reply(call);
839 	if (ret < 0)
840 		return ret;
841 
842 	/* unmarshall the reply once we've received all of it */
843 	bp = call->buffer;
844 	xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode, NULL);
845 	xdr_decode_AFSFetchStatus(&bp, &dvnode->status, dvnode, NULL);
846 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
847 
848 	_leave(" = 0 [done]");
849 	return 0;
850 }
851 
852 /*
853  * FS.Link operation type
854  */
855 static const struct afs_call_type afs_RXFSLink = {
856 	.name		= "FS.Link",
857 	.deliver	= afs_deliver_fs_link,
858 	.abort_to_error	= afs_abort_to_error,
859 	.destructor	= afs_flat_call_destructor,
860 };
861 
862 /*
863  * make a hard link
864  */
865 int afs_fs_link(struct afs_server *server,
866 		struct key *key,
867 		struct afs_vnode *dvnode,
868 		struct afs_vnode *vnode,
869 		const char *name,
870 		bool async)
871 {
872 	struct afs_call *call;
873 	size_t namesz, reqsz, padsz;
874 	__be32 *bp;
875 
876 	_enter("");
877 
878 	namesz = strlen(name);
879 	padsz = (4 - (namesz & 3)) & 3;
880 	reqsz = (5 * 4) + namesz + padsz + (3 * 4);
881 
882 	call = afs_alloc_flat_call(&afs_RXFSLink, reqsz, (21 + 21 + 6) * 4);
883 	if (!call)
884 		return -ENOMEM;
885 
886 	call->key = key;
887 	call->reply = dvnode;
888 	call->reply2 = vnode;
889 	call->service_id = FS_SERVICE;
890 	call->port = htons(AFS_FS_PORT);
891 
892 	/* marshall the parameters */
893 	bp = call->request;
894 	*bp++ = htonl(FSLINK);
895 	*bp++ = htonl(dvnode->fid.vid);
896 	*bp++ = htonl(dvnode->fid.vnode);
897 	*bp++ = htonl(dvnode->fid.unique);
898 	*bp++ = htonl(namesz);
899 	memcpy(bp, name, namesz);
900 	bp = (void *) bp + namesz;
901 	if (padsz > 0) {
902 		memset(bp, 0, padsz);
903 		bp = (void *) bp + padsz;
904 	}
905 	*bp++ = htonl(vnode->fid.vid);
906 	*bp++ = htonl(vnode->fid.vnode);
907 	*bp++ = htonl(vnode->fid.unique);
908 
909 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
910 }
911 
912 /*
913  * deliver reply data to an FS.Symlink
914  */
915 static int afs_deliver_fs_symlink(struct afs_call *call)
916 {
917 	struct afs_vnode *vnode = call->reply;
918 	const __be32 *bp;
919 	int ret;
920 
921 	_enter("{%u}", call->unmarshall);
922 
923 	ret = afs_transfer_reply(call);
924 	if (ret < 0)
925 		return ret;
926 
927 	/* unmarshall the reply once we've received all of it */
928 	bp = call->buffer;
929 	xdr_decode_AFSFid(&bp, call->reply2);
930 	xdr_decode_AFSFetchStatus(&bp, call->reply3, NULL, NULL);
931 	xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode, NULL);
932 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
933 
934 	_leave(" = 0 [done]");
935 	return 0;
936 }
937 
938 /*
939  * FS.Symlink operation type
940  */
941 static const struct afs_call_type afs_RXFSSymlink = {
942 	.name		= "FS.Symlink",
943 	.deliver	= afs_deliver_fs_symlink,
944 	.abort_to_error	= afs_abort_to_error,
945 	.destructor	= afs_flat_call_destructor,
946 };
947 
948 /*
949  * create a symbolic link
950  */
951 int afs_fs_symlink(struct afs_server *server,
952 		   struct key *key,
953 		   struct afs_vnode *vnode,
954 		   const char *name,
955 		   const char *contents,
956 		   struct afs_fid *newfid,
957 		   struct afs_file_status *newstatus,
958 		   bool async)
959 {
960 	struct afs_call *call;
961 	size_t namesz, reqsz, padsz, c_namesz, c_padsz;
962 	__be32 *bp;
963 
964 	_enter("");
965 
966 	namesz = strlen(name);
967 	padsz = (4 - (namesz & 3)) & 3;
968 
969 	c_namesz = strlen(contents);
970 	c_padsz = (4 - (c_namesz & 3)) & 3;
971 
972 	reqsz = (6 * 4) + namesz + padsz + c_namesz + c_padsz + (6 * 4);
973 
974 	call = afs_alloc_flat_call(&afs_RXFSSymlink, reqsz,
975 				   (3 + 21 + 21 + 6) * 4);
976 	if (!call)
977 		return -ENOMEM;
978 
979 	call->key = key;
980 	call->reply = vnode;
981 	call->reply2 = newfid;
982 	call->reply3 = newstatus;
983 	call->service_id = FS_SERVICE;
984 	call->port = htons(AFS_FS_PORT);
985 
986 	/* marshall the parameters */
987 	bp = call->request;
988 	*bp++ = htonl(FSSYMLINK);
989 	*bp++ = htonl(vnode->fid.vid);
990 	*bp++ = htonl(vnode->fid.vnode);
991 	*bp++ = htonl(vnode->fid.unique);
992 	*bp++ = htonl(namesz);
993 	memcpy(bp, name, namesz);
994 	bp = (void *) bp + namesz;
995 	if (padsz > 0) {
996 		memset(bp, 0, padsz);
997 		bp = (void *) bp + padsz;
998 	}
999 	*bp++ = htonl(c_namesz);
1000 	memcpy(bp, contents, c_namesz);
1001 	bp = (void *) bp + c_namesz;
1002 	if (c_padsz > 0) {
1003 		memset(bp, 0, c_padsz);
1004 		bp = (void *) bp + c_padsz;
1005 	}
1006 	*bp++ = htonl(AFS_SET_MODE | AFS_SET_MTIME);
1007 	*bp++ = htonl(vnode->vfs_inode.i_mtime.tv_sec); /* mtime */
1008 	*bp++ = 0; /* owner */
1009 	*bp++ = 0; /* group */
1010 	*bp++ = htonl(S_IRWXUGO); /* unix mode */
1011 	*bp++ = 0; /* segment size */
1012 
1013 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1014 }
1015 
1016 /*
1017  * deliver reply data to an FS.Rename
1018  */
1019 static int afs_deliver_fs_rename(struct afs_call *call)
1020 {
1021 	struct afs_vnode *orig_dvnode = call->reply, *new_dvnode = call->reply2;
1022 	const __be32 *bp;
1023 	int ret;
1024 
1025 	_enter("{%u}", call->unmarshall);
1026 
1027 	ret = afs_transfer_reply(call);
1028 	if (ret < 0)
1029 		return ret;
1030 
1031 	/* unmarshall the reply once we've received all of it */
1032 	bp = call->buffer;
1033 	xdr_decode_AFSFetchStatus(&bp, &orig_dvnode->status, orig_dvnode, NULL);
1034 	if (new_dvnode != orig_dvnode)
1035 		xdr_decode_AFSFetchStatus(&bp, &new_dvnode->status, new_dvnode,
1036 					  NULL);
1037 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
1038 
1039 	_leave(" = 0 [done]");
1040 	return 0;
1041 }
1042 
1043 /*
1044  * FS.Rename operation type
1045  */
1046 static const struct afs_call_type afs_RXFSRename = {
1047 	.name		= "FS.Rename",
1048 	.deliver	= afs_deliver_fs_rename,
1049 	.abort_to_error	= afs_abort_to_error,
1050 	.destructor	= afs_flat_call_destructor,
1051 };
1052 
1053 /*
1054  * create a symbolic link
1055  */
1056 int afs_fs_rename(struct afs_server *server,
1057 		  struct key *key,
1058 		  struct afs_vnode *orig_dvnode,
1059 		  const char *orig_name,
1060 		  struct afs_vnode *new_dvnode,
1061 		  const char *new_name,
1062 		  bool async)
1063 {
1064 	struct afs_call *call;
1065 	size_t reqsz, o_namesz, o_padsz, n_namesz, n_padsz;
1066 	__be32 *bp;
1067 
1068 	_enter("");
1069 
1070 	o_namesz = strlen(orig_name);
1071 	o_padsz = (4 - (o_namesz & 3)) & 3;
1072 
1073 	n_namesz = strlen(new_name);
1074 	n_padsz = (4 - (n_namesz & 3)) & 3;
1075 
1076 	reqsz = (4 * 4) +
1077 		4 + o_namesz + o_padsz +
1078 		(3 * 4) +
1079 		4 + n_namesz + n_padsz;
1080 
1081 	call = afs_alloc_flat_call(&afs_RXFSRename, reqsz, (21 + 21 + 6) * 4);
1082 	if (!call)
1083 		return -ENOMEM;
1084 
1085 	call->key = key;
1086 	call->reply = orig_dvnode;
1087 	call->reply2 = new_dvnode;
1088 	call->service_id = FS_SERVICE;
1089 	call->port = htons(AFS_FS_PORT);
1090 
1091 	/* marshall the parameters */
1092 	bp = call->request;
1093 	*bp++ = htonl(FSRENAME);
1094 	*bp++ = htonl(orig_dvnode->fid.vid);
1095 	*bp++ = htonl(orig_dvnode->fid.vnode);
1096 	*bp++ = htonl(orig_dvnode->fid.unique);
1097 	*bp++ = htonl(o_namesz);
1098 	memcpy(bp, orig_name, o_namesz);
1099 	bp = (void *) bp + o_namesz;
1100 	if (o_padsz > 0) {
1101 		memset(bp, 0, o_padsz);
1102 		bp = (void *) bp + o_padsz;
1103 	}
1104 
1105 	*bp++ = htonl(new_dvnode->fid.vid);
1106 	*bp++ = htonl(new_dvnode->fid.vnode);
1107 	*bp++ = htonl(new_dvnode->fid.unique);
1108 	*bp++ = htonl(n_namesz);
1109 	memcpy(bp, new_name, n_namesz);
1110 	bp = (void *) bp + n_namesz;
1111 	if (n_padsz > 0) {
1112 		memset(bp, 0, n_padsz);
1113 		bp = (void *) bp + n_padsz;
1114 	}
1115 
1116 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1117 }
1118 
1119 /*
1120  * deliver reply data to an FS.StoreData
1121  */
1122 static int afs_deliver_fs_store_data(struct afs_call *call)
1123 {
1124 	struct afs_vnode *vnode = call->reply;
1125 	const __be32 *bp;
1126 	int ret;
1127 
1128 	_enter("");
1129 
1130 	ret = afs_transfer_reply(call);
1131 	if (ret < 0)
1132 		return ret;
1133 
1134 	/* unmarshall the reply once we've received all of it */
1135 	bp = call->buffer;
1136 	xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode,
1137 				  &call->store_version);
1138 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
1139 
1140 	afs_pages_written_back(vnode, call);
1141 
1142 	_leave(" = 0 [done]");
1143 	return 0;
1144 }
1145 
1146 /*
1147  * FS.StoreData operation type
1148  */
1149 static const struct afs_call_type afs_RXFSStoreData = {
1150 	.name		= "FS.StoreData",
1151 	.deliver	= afs_deliver_fs_store_data,
1152 	.abort_to_error	= afs_abort_to_error,
1153 	.destructor	= afs_flat_call_destructor,
1154 };
1155 
1156 static const struct afs_call_type afs_RXFSStoreData64 = {
1157 	.name		= "FS.StoreData64",
1158 	.deliver	= afs_deliver_fs_store_data,
1159 	.abort_to_error	= afs_abort_to_error,
1160 	.destructor	= afs_flat_call_destructor,
1161 };
1162 
1163 /*
1164  * store a set of pages to a very large file
1165  */
1166 static int afs_fs_store_data64(struct afs_server *server,
1167 			       struct afs_writeback *wb,
1168 			       pgoff_t first, pgoff_t last,
1169 			       unsigned offset, unsigned to,
1170 			       loff_t size, loff_t pos, loff_t i_size,
1171 			       bool async)
1172 {
1173 	struct afs_vnode *vnode = wb->vnode;
1174 	struct afs_call *call;
1175 	__be32 *bp;
1176 
1177 	_enter(",%x,{%x:%u},,",
1178 	       key_serial(wb->key), vnode->fid.vid, vnode->fid.vnode);
1179 
1180 	call = afs_alloc_flat_call(&afs_RXFSStoreData64,
1181 				   (4 + 6 + 3 * 2) * 4,
1182 				   (21 + 6) * 4);
1183 	if (!call)
1184 		return -ENOMEM;
1185 
1186 	call->wb = wb;
1187 	call->key = wb->key;
1188 	call->reply = vnode;
1189 	call->service_id = FS_SERVICE;
1190 	call->port = htons(AFS_FS_PORT);
1191 	call->mapping = vnode->vfs_inode.i_mapping;
1192 	call->first = first;
1193 	call->last = last;
1194 	call->first_offset = offset;
1195 	call->last_to = to;
1196 	call->send_pages = true;
1197 	call->store_version = vnode->status.data_version + 1;
1198 
1199 	/* marshall the parameters */
1200 	bp = call->request;
1201 	*bp++ = htonl(FSSTOREDATA64);
1202 	*bp++ = htonl(vnode->fid.vid);
1203 	*bp++ = htonl(vnode->fid.vnode);
1204 	*bp++ = htonl(vnode->fid.unique);
1205 
1206 	*bp++ = htonl(AFS_SET_MTIME); /* mask */
1207 	*bp++ = htonl(vnode->vfs_inode.i_mtime.tv_sec); /* mtime */
1208 	*bp++ = 0; /* owner */
1209 	*bp++ = 0; /* group */
1210 	*bp++ = 0; /* unix mode */
1211 	*bp++ = 0; /* segment size */
1212 
1213 	*bp++ = htonl(pos >> 32);
1214 	*bp++ = htonl((u32) pos);
1215 	*bp++ = htonl(size >> 32);
1216 	*bp++ = htonl((u32) size);
1217 	*bp++ = htonl(i_size >> 32);
1218 	*bp++ = htonl((u32) i_size);
1219 
1220 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1221 }
1222 
1223 /*
1224  * store a set of pages
1225  */
1226 int afs_fs_store_data(struct afs_server *server, struct afs_writeback *wb,
1227 		      pgoff_t first, pgoff_t last,
1228 		      unsigned offset, unsigned to,
1229 		      bool async)
1230 {
1231 	struct afs_vnode *vnode = wb->vnode;
1232 	struct afs_call *call;
1233 	loff_t size, pos, i_size;
1234 	__be32 *bp;
1235 
1236 	_enter(",%x,{%x:%u},,",
1237 	       key_serial(wb->key), vnode->fid.vid, vnode->fid.vnode);
1238 
1239 	size = (loff_t)to - (loff_t)offset;
1240 	if (first != last)
1241 		size += (loff_t)(last - first) << PAGE_SHIFT;
1242 	pos = (loff_t)first << PAGE_SHIFT;
1243 	pos += offset;
1244 
1245 	i_size = i_size_read(&vnode->vfs_inode);
1246 	if (pos + size > i_size)
1247 		i_size = size + pos;
1248 
1249 	_debug("size %llx, at %llx, i_size %llx",
1250 	       (unsigned long long) size, (unsigned long long) pos,
1251 	       (unsigned long long) i_size);
1252 
1253 	if (pos >> 32 || i_size >> 32 || size >> 32 || (pos + size) >> 32)
1254 		return afs_fs_store_data64(server, wb, first, last, offset, to,
1255 					   size, pos, i_size, async);
1256 
1257 	call = afs_alloc_flat_call(&afs_RXFSStoreData,
1258 				   (4 + 6 + 3) * 4,
1259 				   (21 + 6) * 4);
1260 	if (!call)
1261 		return -ENOMEM;
1262 
1263 	call->wb = wb;
1264 	call->key = wb->key;
1265 	call->reply = vnode;
1266 	call->service_id = FS_SERVICE;
1267 	call->port = htons(AFS_FS_PORT);
1268 	call->mapping = vnode->vfs_inode.i_mapping;
1269 	call->first = first;
1270 	call->last = last;
1271 	call->first_offset = offset;
1272 	call->last_to = to;
1273 	call->send_pages = true;
1274 	call->store_version = vnode->status.data_version + 1;
1275 
1276 	/* marshall the parameters */
1277 	bp = call->request;
1278 	*bp++ = htonl(FSSTOREDATA);
1279 	*bp++ = htonl(vnode->fid.vid);
1280 	*bp++ = htonl(vnode->fid.vnode);
1281 	*bp++ = htonl(vnode->fid.unique);
1282 
1283 	*bp++ = htonl(AFS_SET_MTIME); /* mask */
1284 	*bp++ = htonl(vnode->vfs_inode.i_mtime.tv_sec); /* mtime */
1285 	*bp++ = 0; /* owner */
1286 	*bp++ = 0; /* group */
1287 	*bp++ = 0; /* unix mode */
1288 	*bp++ = 0; /* segment size */
1289 
1290 	*bp++ = htonl(pos);
1291 	*bp++ = htonl(size);
1292 	*bp++ = htonl(i_size);
1293 
1294 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1295 }
1296 
1297 /*
1298  * deliver reply data to an FS.StoreStatus
1299  */
1300 static int afs_deliver_fs_store_status(struct afs_call *call)
1301 {
1302 	afs_dataversion_t *store_version;
1303 	struct afs_vnode *vnode = call->reply;
1304 	const __be32 *bp;
1305 	int ret;
1306 
1307 	_enter("");
1308 
1309 	ret = afs_transfer_reply(call);
1310 	if (ret < 0)
1311 		return ret;
1312 
1313 	/* unmarshall the reply once we've received all of it */
1314 	store_version = NULL;
1315 	if (call->operation_ID == FSSTOREDATA)
1316 		store_version = &call->store_version;
1317 
1318 	bp = call->buffer;
1319 	xdr_decode_AFSFetchStatus(&bp, &vnode->status, vnode, store_version);
1320 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
1321 
1322 	_leave(" = 0 [done]");
1323 	return 0;
1324 }
1325 
1326 /*
1327  * FS.StoreStatus operation type
1328  */
1329 static const struct afs_call_type afs_RXFSStoreStatus = {
1330 	.name		= "FS.StoreStatus",
1331 	.deliver	= afs_deliver_fs_store_status,
1332 	.abort_to_error	= afs_abort_to_error,
1333 	.destructor	= afs_flat_call_destructor,
1334 };
1335 
1336 static const struct afs_call_type afs_RXFSStoreData_as_Status = {
1337 	.name		= "FS.StoreData",
1338 	.deliver	= afs_deliver_fs_store_status,
1339 	.abort_to_error	= afs_abort_to_error,
1340 	.destructor	= afs_flat_call_destructor,
1341 };
1342 
1343 static const struct afs_call_type afs_RXFSStoreData64_as_Status = {
1344 	.name		= "FS.StoreData64",
1345 	.deliver	= afs_deliver_fs_store_status,
1346 	.abort_to_error	= afs_abort_to_error,
1347 	.destructor	= afs_flat_call_destructor,
1348 };
1349 
1350 /*
1351  * set the attributes on a very large file, using FS.StoreData rather than
1352  * FS.StoreStatus so as to alter the file size also
1353  */
1354 static int afs_fs_setattr_size64(struct afs_server *server, struct key *key,
1355 				 struct afs_vnode *vnode, struct iattr *attr,
1356 				 bool async)
1357 {
1358 	struct afs_call *call;
1359 	__be32 *bp;
1360 
1361 	_enter(",%x,{%x:%u},,",
1362 	       key_serial(key), vnode->fid.vid, vnode->fid.vnode);
1363 
1364 	ASSERT(attr->ia_valid & ATTR_SIZE);
1365 
1366 	call = afs_alloc_flat_call(&afs_RXFSStoreData64_as_Status,
1367 				   (4 + 6 + 3 * 2) * 4,
1368 				   (21 + 6) * 4);
1369 	if (!call)
1370 		return -ENOMEM;
1371 
1372 	call->key = key;
1373 	call->reply = vnode;
1374 	call->service_id = FS_SERVICE;
1375 	call->port = htons(AFS_FS_PORT);
1376 	call->store_version = vnode->status.data_version + 1;
1377 	call->operation_ID = FSSTOREDATA;
1378 
1379 	/* marshall the parameters */
1380 	bp = call->request;
1381 	*bp++ = htonl(FSSTOREDATA64);
1382 	*bp++ = htonl(vnode->fid.vid);
1383 	*bp++ = htonl(vnode->fid.vnode);
1384 	*bp++ = htonl(vnode->fid.unique);
1385 
1386 	xdr_encode_AFS_StoreStatus(&bp, attr);
1387 
1388 	*bp++ = 0;				/* position of start of write */
1389 	*bp++ = 0;
1390 	*bp++ = 0;				/* size of write */
1391 	*bp++ = 0;
1392 	*bp++ = htonl(attr->ia_size >> 32);	/* new file length */
1393 	*bp++ = htonl((u32) attr->ia_size);
1394 
1395 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1396 }
1397 
1398 /*
1399  * set the attributes on a file, using FS.StoreData rather than FS.StoreStatus
1400  * so as to alter the file size also
1401  */
1402 static int afs_fs_setattr_size(struct afs_server *server, struct key *key,
1403 			       struct afs_vnode *vnode, struct iattr *attr,
1404 			       bool async)
1405 {
1406 	struct afs_call *call;
1407 	__be32 *bp;
1408 
1409 	_enter(",%x,{%x:%u},,",
1410 	       key_serial(key), vnode->fid.vid, vnode->fid.vnode);
1411 
1412 	ASSERT(attr->ia_valid & ATTR_SIZE);
1413 	if (attr->ia_size >> 32)
1414 		return afs_fs_setattr_size64(server, key, vnode, attr,
1415 					     async);
1416 
1417 	call = afs_alloc_flat_call(&afs_RXFSStoreData_as_Status,
1418 				   (4 + 6 + 3) * 4,
1419 				   (21 + 6) * 4);
1420 	if (!call)
1421 		return -ENOMEM;
1422 
1423 	call->key = key;
1424 	call->reply = vnode;
1425 	call->service_id = FS_SERVICE;
1426 	call->port = htons(AFS_FS_PORT);
1427 	call->store_version = vnode->status.data_version + 1;
1428 	call->operation_ID = FSSTOREDATA;
1429 
1430 	/* marshall the parameters */
1431 	bp = call->request;
1432 	*bp++ = htonl(FSSTOREDATA);
1433 	*bp++ = htonl(vnode->fid.vid);
1434 	*bp++ = htonl(vnode->fid.vnode);
1435 	*bp++ = htonl(vnode->fid.unique);
1436 
1437 	xdr_encode_AFS_StoreStatus(&bp, attr);
1438 
1439 	*bp++ = 0;				/* position of start of write */
1440 	*bp++ = 0;				/* size of write */
1441 	*bp++ = htonl(attr->ia_size);		/* new file length */
1442 
1443 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1444 }
1445 
1446 /*
1447  * set the attributes on a file, using FS.StoreData if there's a change in file
1448  * size, and FS.StoreStatus otherwise
1449  */
1450 int afs_fs_setattr(struct afs_server *server, struct key *key,
1451 		   struct afs_vnode *vnode, struct iattr *attr,
1452 		   bool async)
1453 {
1454 	struct afs_call *call;
1455 	__be32 *bp;
1456 
1457 	if (attr->ia_valid & ATTR_SIZE)
1458 		return afs_fs_setattr_size(server, key, vnode, attr,
1459 					   async);
1460 
1461 	_enter(",%x,{%x:%u},,",
1462 	       key_serial(key), vnode->fid.vid, vnode->fid.vnode);
1463 
1464 	call = afs_alloc_flat_call(&afs_RXFSStoreStatus,
1465 				   (4 + 6) * 4,
1466 				   (21 + 6) * 4);
1467 	if (!call)
1468 		return -ENOMEM;
1469 
1470 	call->key = key;
1471 	call->reply = vnode;
1472 	call->service_id = FS_SERVICE;
1473 	call->port = htons(AFS_FS_PORT);
1474 	call->operation_ID = FSSTORESTATUS;
1475 
1476 	/* marshall the parameters */
1477 	bp = call->request;
1478 	*bp++ = htonl(FSSTORESTATUS);
1479 	*bp++ = htonl(vnode->fid.vid);
1480 	*bp++ = htonl(vnode->fid.vnode);
1481 	*bp++ = htonl(vnode->fid.unique);
1482 
1483 	xdr_encode_AFS_StoreStatus(&bp, attr);
1484 
1485 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1486 }
1487 
1488 /*
1489  * deliver reply data to an FS.GetVolumeStatus
1490  */
1491 static int afs_deliver_fs_get_volume_status(struct afs_call *call)
1492 {
1493 	const __be32 *bp;
1494 	char *p;
1495 	int ret;
1496 
1497 	_enter("{%u}", call->unmarshall);
1498 
1499 	switch (call->unmarshall) {
1500 	case 0:
1501 		call->offset = 0;
1502 		call->unmarshall++;
1503 
1504 		/* extract the returned status record */
1505 	case 1:
1506 		_debug("extract status");
1507 		ret = afs_extract_data(call, call->buffer,
1508 				       12 * 4, true);
1509 		if (ret < 0)
1510 			return ret;
1511 
1512 		bp = call->buffer;
1513 		xdr_decode_AFSFetchVolumeStatus(&bp, call->reply2);
1514 		call->offset = 0;
1515 		call->unmarshall++;
1516 
1517 		/* extract the volume name length */
1518 	case 2:
1519 		ret = afs_extract_data(call, &call->tmp, 4, true);
1520 		if (ret < 0)
1521 			return ret;
1522 
1523 		call->count = ntohl(call->tmp);
1524 		_debug("volname length: %u", call->count);
1525 		if (call->count >= AFSNAMEMAX)
1526 			return -EBADMSG;
1527 		call->offset = 0;
1528 		call->unmarshall++;
1529 
1530 		/* extract the volume name */
1531 	case 3:
1532 		_debug("extract volname");
1533 		if (call->count > 0) {
1534 			ret = afs_extract_data(call, call->reply3,
1535 					       call->count, true);
1536 			if (ret < 0)
1537 				return ret;
1538 		}
1539 
1540 		p = call->reply3;
1541 		p[call->count] = 0;
1542 		_debug("volname '%s'", p);
1543 
1544 		call->offset = 0;
1545 		call->unmarshall++;
1546 
1547 		/* extract the volume name padding */
1548 		if ((call->count & 3) == 0) {
1549 			call->unmarshall++;
1550 			goto no_volname_padding;
1551 		}
1552 		call->count = 4 - (call->count & 3);
1553 
1554 	case 4:
1555 		ret = afs_extract_data(call, call->buffer,
1556 				       call->count, true);
1557 		if (ret < 0)
1558 			return ret;
1559 
1560 		call->offset = 0;
1561 		call->unmarshall++;
1562 	no_volname_padding:
1563 
1564 		/* extract the offline message length */
1565 	case 5:
1566 		ret = afs_extract_data(call, &call->tmp, 4, true);
1567 		if (ret < 0)
1568 			return ret;
1569 
1570 		call->count = ntohl(call->tmp);
1571 		_debug("offline msg length: %u", call->count);
1572 		if (call->count >= AFSNAMEMAX)
1573 			return -EBADMSG;
1574 		call->offset = 0;
1575 		call->unmarshall++;
1576 
1577 		/* extract the offline message */
1578 	case 6:
1579 		_debug("extract offline");
1580 		if (call->count > 0) {
1581 			ret = afs_extract_data(call, call->reply3,
1582 					       call->count, true);
1583 			if (ret < 0)
1584 				return ret;
1585 		}
1586 
1587 		p = call->reply3;
1588 		p[call->count] = 0;
1589 		_debug("offline '%s'", p);
1590 
1591 		call->offset = 0;
1592 		call->unmarshall++;
1593 
1594 		/* extract the offline message padding */
1595 		if ((call->count & 3) == 0) {
1596 			call->unmarshall++;
1597 			goto no_offline_padding;
1598 		}
1599 		call->count = 4 - (call->count & 3);
1600 
1601 	case 7:
1602 		ret = afs_extract_data(call, call->buffer,
1603 				       call->count, true);
1604 		if (ret < 0)
1605 			return ret;
1606 
1607 		call->offset = 0;
1608 		call->unmarshall++;
1609 	no_offline_padding:
1610 
1611 		/* extract the message of the day length */
1612 	case 8:
1613 		ret = afs_extract_data(call, &call->tmp, 4, true);
1614 		if (ret < 0)
1615 			return ret;
1616 
1617 		call->count = ntohl(call->tmp);
1618 		_debug("motd length: %u", call->count);
1619 		if (call->count >= AFSNAMEMAX)
1620 			return -EBADMSG;
1621 		call->offset = 0;
1622 		call->unmarshall++;
1623 
1624 		/* extract the message of the day */
1625 	case 9:
1626 		_debug("extract motd");
1627 		if (call->count > 0) {
1628 			ret = afs_extract_data(call, call->reply3,
1629 					       call->count, true);
1630 			if (ret < 0)
1631 				return ret;
1632 		}
1633 
1634 		p = call->reply3;
1635 		p[call->count] = 0;
1636 		_debug("motd '%s'", p);
1637 
1638 		call->offset = 0;
1639 		call->unmarshall++;
1640 
1641 		/* extract the message of the day padding */
1642 		call->count = (4 - (call->count & 3)) & 3;
1643 
1644 	case 10:
1645 		ret = afs_extract_data(call, call->buffer,
1646 				       call->count, false);
1647 		if (ret < 0)
1648 			return ret;
1649 
1650 		call->offset = 0;
1651 		call->unmarshall++;
1652 	case 11:
1653 		break;
1654 	}
1655 
1656 	_leave(" = 0 [done]");
1657 	return 0;
1658 }
1659 
1660 /*
1661  * destroy an FS.GetVolumeStatus call
1662  */
1663 static void afs_get_volume_status_call_destructor(struct afs_call *call)
1664 {
1665 	kfree(call->reply3);
1666 	call->reply3 = NULL;
1667 	afs_flat_call_destructor(call);
1668 }
1669 
1670 /*
1671  * FS.GetVolumeStatus operation type
1672  */
1673 static const struct afs_call_type afs_RXFSGetVolumeStatus = {
1674 	.name		= "FS.GetVolumeStatus",
1675 	.deliver	= afs_deliver_fs_get_volume_status,
1676 	.abort_to_error	= afs_abort_to_error,
1677 	.destructor	= afs_get_volume_status_call_destructor,
1678 };
1679 
1680 /*
1681  * fetch the status of a volume
1682  */
1683 int afs_fs_get_volume_status(struct afs_server *server,
1684 			     struct key *key,
1685 			     struct afs_vnode *vnode,
1686 			     struct afs_volume_status *vs,
1687 			     bool async)
1688 {
1689 	struct afs_call *call;
1690 	__be32 *bp;
1691 	void *tmpbuf;
1692 
1693 	_enter("");
1694 
1695 	tmpbuf = kmalloc(AFSOPAQUEMAX, GFP_KERNEL);
1696 	if (!tmpbuf)
1697 		return -ENOMEM;
1698 
1699 	call = afs_alloc_flat_call(&afs_RXFSGetVolumeStatus, 2 * 4, 12 * 4);
1700 	if (!call) {
1701 		kfree(tmpbuf);
1702 		return -ENOMEM;
1703 	}
1704 
1705 	call->key = key;
1706 	call->reply = vnode;
1707 	call->reply2 = vs;
1708 	call->reply3 = tmpbuf;
1709 	call->service_id = FS_SERVICE;
1710 	call->port = htons(AFS_FS_PORT);
1711 
1712 	/* marshall the parameters */
1713 	bp = call->request;
1714 	bp[0] = htonl(FSGETVOLUMESTATUS);
1715 	bp[1] = htonl(vnode->fid.vid);
1716 
1717 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1718 }
1719 
1720 /*
1721  * deliver reply data to an FS.SetLock, FS.ExtendLock or FS.ReleaseLock
1722  */
1723 static int afs_deliver_fs_xxxx_lock(struct afs_call *call)
1724 {
1725 	const __be32 *bp;
1726 	int ret;
1727 
1728 	_enter("{%u}", call->unmarshall);
1729 
1730 	ret = afs_transfer_reply(call);
1731 	if (ret < 0)
1732 		return ret;
1733 
1734 	/* unmarshall the reply once we've received all of it */
1735 	bp = call->buffer;
1736 	/* xdr_decode_AFSVolSync(&bp, call->replyX); */
1737 
1738 	_leave(" = 0 [done]");
1739 	return 0;
1740 }
1741 
1742 /*
1743  * FS.SetLock operation type
1744  */
1745 static const struct afs_call_type afs_RXFSSetLock = {
1746 	.name		= "FS.SetLock",
1747 	.deliver	= afs_deliver_fs_xxxx_lock,
1748 	.abort_to_error	= afs_abort_to_error,
1749 	.destructor	= afs_flat_call_destructor,
1750 };
1751 
1752 /*
1753  * FS.ExtendLock operation type
1754  */
1755 static const struct afs_call_type afs_RXFSExtendLock = {
1756 	.name		= "FS.ExtendLock",
1757 	.deliver	= afs_deliver_fs_xxxx_lock,
1758 	.abort_to_error	= afs_abort_to_error,
1759 	.destructor	= afs_flat_call_destructor,
1760 };
1761 
1762 /*
1763  * FS.ReleaseLock operation type
1764  */
1765 static const struct afs_call_type afs_RXFSReleaseLock = {
1766 	.name		= "FS.ReleaseLock",
1767 	.deliver	= afs_deliver_fs_xxxx_lock,
1768 	.abort_to_error	= afs_abort_to_error,
1769 	.destructor	= afs_flat_call_destructor,
1770 };
1771 
1772 /*
1773  * get a lock on a file
1774  */
1775 int afs_fs_set_lock(struct afs_server *server,
1776 		    struct key *key,
1777 		    struct afs_vnode *vnode,
1778 		    afs_lock_type_t type,
1779 		    bool async)
1780 {
1781 	struct afs_call *call;
1782 	__be32 *bp;
1783 
1784 	_enter("");
1785 
1786 	call = afs_alloc_flat_call(&afs_RXFSSetLock, 5 * 4, 6 * 4);
1787 	if (!call)
1788 		return -ENOMEM;
1789 
1790 	call->key = key;
1791 	call->reply = vnode;
1792 	call->service_id = FS_SERVICE;
1793 	call->port = htons(AFS_FS_PORT);
1794 
1795 	/* marshall the parameters */
1796 	bp = call->request;
1797 	*bp++ = htonl(FSSETLOCK);
1798 	*bp++ = htonl(vnode->fid.vid);
1799 	*bp++ = htonl(vnode->fid.vnode);
1800 	*bp++ = htonl(vnode->fid.unique);
1801 	*bp++ = htonl(type);
1802 
1803 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1804 }
1805 
1806 /*
1807  * extend a lock on a file
1808  */
1809 int afs_fs_extend_lock(struct afs_server *server,
1810 		       struct key *key,
1811 		       struct afs_vnode *vnode,
1812 		       bool async)
1813 {
1814 	struct afs_call *call;
1815 	__be32 *bp;
1816 
1817 	_enter("");
1818 
1819 	call = afs_alloc_flat_call(&afs_RXFSExtendLock, 4 * 4, 6 * 4);
1820 	if (!call)
1821 		return -ENOMEM;
1822 
1823 	call->key = key;
1824 	call->reply = vnode;
1825 	call->service_id = FS_SERVICE;
1826 	call->port = htons(AFS_FS_PORT);
1827 
1828 	/* marshall the parameters */
1829 	bp = call->request;
1830 	*bp++ = htonl(FSEXTENDLOCK);
1831 	*bp++ = htonl(vnode->fid.vid);
1832 	*bp++ = htonl(vnode->fid.vnode);
1833 	*bp++ = htonl(vnode->fid.unique);
1834 
1835 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1836 }
1837 
1838 /*
1839  * release a lock on a file
1840  */
1841 int afs_fs_release_lock(struct afs_server *server,
1842 			struct key *key,
1843 			struct afs_vnode *vnode,
1844 			bool async)
1845 {
1846 	struct afs_call *call;
1847 	__be32 *bp;
1848 
1849 	_enter("");
1850 
1851 	call = afs_alloc_flat_call(&afs_RXFSReleaseLock, 4 * 4, 6 * 4);
1852 	if (!call)
1853 		return -ENOMEM;
1854 
1855 	call->key = key;
1856 	call->reply = vnode;
1857 	call->service_id = FS_SERVICE;
1858 	call->port = htons(AFS_FS_PORT);
1859 
1860 	/* marshall the parameters */
1861 	bp = call->request;
1862 	*bp++ = htonl(FSRELEASELOCK);
1863 	*bp++ = htonl(vnode->fid.vid);
1864 	*bp++ = htonl(vnode->fid.vnode);
1865 	*bp++ = htonl(vnode->fid.unique);
1866 
1867 	return afs_make_call(&server->addr, call, GFP_NOFS, async);
1868 }
1869