1 /* YFS File Server client stubs 2 * 3 * Copyright (C) 2018 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 Licence 8 * as published by the Free Software Foundation; either version 9 * 2 of the Licence, 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 <linux/iversion.h> 17 #include "internal.h" 18 #include "afs_fs.h" 19 #include "xdr_fs.h" 20 #include "protocol_yfs.h" 21 22 static const struct afs_fid afs_zero_fid; 23 24 static inline void afs_use_fs_server(struct afs_call *call, struct afs_cb_interest *cbi) 25 { 26 call->cbi = afs_get_cb_interest(cbi); 27 } 28 29 #define xdr_size(x) (sizeof(*x) / sizeof(__be32)) 30 31 static void xdr_decode_YFSFid(const __be32 **_bp, struct afs_fid *fid) 32 { 33 const struct yfs_xdr_YFSFid *x = (const void *)*_bp; 34 35 fid->vid = xdr_to_u64(x->volume); 36 fid->vnode = xdr_to_u64(x->vnode.lo); 37 fid->vnode_hi = ntohl(x->vnode.hi); 38 fid->unique = ntohl(x->vnode.unique); 39 *_bp += xdr_size(x); 40 } 41 42 static __be32 *xdr_encode_u32(__be32 *bp, u32 n) 43 { 44 *bp++ = htonl(n); 45 return bp; 46 } 47 48 static __be32 *xdr_encode_u64(__be32 *bp, u64 n) 49 { 50 struct yfs_xdr_u64 *x = (void *)bp; 51 52 *x = u64_to_xdr(n); 53 return bp + xdr_size(x); 54 } 55 56 static __be32 *xdr_encode_YFSFid(__be32 *bp, struct afs_fid *fid) 57 { 58 struct yfs_xdr_YFSFid *x = (void *)bp; 59 60 x->volume = u64_to_xdr(fid->vid); 61 x->vnode.lo = u64_to_xdr(fid->vnode); 62 x->vnode.hi = htonl(fid->vnode_hi); 63 x->vnode.unique = htonl(fid->unique); 64 return bp + xdr_size(x); 65 } 66 67 static size_t xdr_strlen(unsigned int len) 68 { 69 return sizeof(__be32) + round_up(len, sizeof(__be32)); 70 } 71 72 static __be32 *xdr_encode_string(__be32 *bp, const char *p, unsigned int len) 73 { 74 bp = xdr_encode_u32(bp, len); 75 bp = memcpy(bp, p, len); 76 if (len & 3) { 77 unsigned int pad = 4 - (len & 3); 78 79 memset((u8 *)bp + len, 0, pad); 80 len += pad; 81 } 82 83 return bp + len / sizeof(__be32); 84 } 85 86 static s64 linux_to_yfs_time(const struct timespec64 *t) 87 { 88 /* Convert to 100ns intervals. */ 89 return (u64)t->tv_sec * 10000000 + t->tv_nsec/100; 90 } 91 92 static __be32 *xdr_encode_YFSStoreStatus_mode(__be32 *bp, mode_t mode) 93 { 94 struct yfs_xdr_YFSStoreStatus *x = (void *)bp; 95 96 x->mask = htonl(AFS_SET_MODE); 97 x->mode = htonl(mode & S_IALLUGO); 98 x->mtime_client = u64_to_xdr(0); 99 x->owner = u64_to_xdr(0); 100 x->group = u64_to_xdr(0); 101 return bp + xdr_size(x); 102 } 103 104 static __be32 *xdr_encode_YFSStoreStatus_mtime(__be32 *bp, const struct timespec64 *t) 105 { 106 struct yfs_xdr_YFSStoreStatus *x = (void *)bp; 107 s64 mtime = linux_to_yfs_time(t); 108 109 x->mask = htonl(AFS_SET_MTIME); 110 x->mode = htonl(0); 111 x->mtime_client = u64_to_xdr(mtime); 112 x->owner = u64_to_xdr(0); 113 x->group = u64_to_xdr(0); 114 return bp + xdr_size(x); 115 } 116 117 /* 118 * Convert a signed 100ns-resolution 64-bit time into a timespec. 119 */ 120 static struct timespec64 yfs_time_to_linux(s64 t) 121 { 122 struct timespec64 ts; 123 u64 abs_t; 124 125 /* 126 * Unfortunately can not use normal 64 bit division on 32 bit arch, but 127 * the alternative, do_div, does not work with negative numbers so have 128 * to special case them 129 */ 130 if (t < 0) { 131 abs_t = -t; 132 ts.tv_nsec = (time64_t)(do_div(abs_t, 10000000) * 100); 133 ts.tv_nsec = -ts.tv_nsec; 134 ts.tv_sec = -abs_t; 135 } else { 136 abs_t = t; 137 ts.tv_nsec = (time64_t)do_div(abs_t, 10000000) * 100; 138 ts.tv_sec = abs_t; 139 } 140 141 return ts; 142 } 143 144 static struct timespec64 xdr_to_time(const struct yfs_xdr_u64 xdr) 145 { 146 s64 t = xdr_to_u64(xdr); 147 148 return yfs_time_to_linux(t); 149 } 150 151 static void yfs_check_req(struct afs_call *call, __be32 *bp) 152 { 153 size_t len = (void *)bp - call->request; 154 155 if (len > call->request_size) 156 pr_err("kAFS: %s: Request buffer overflow (%zu>%u)\n", 157 call->type->name, len, call->request_size); 158 else if (len < call->request_size) 159 pr_warning("kAFS: %s: Request buffer underflow (%zu<%u)\n", 160 call->type->name, len, call->request_size); 161 } 162 163 /* 164 * Dump a bad file status record. 165 */ 166 static void xdr_dump_bad(const __be32 *bp) 167 { 168 __be32 x[4]; 169 int i; 170 171 pr_notice("YFS XDR: Bad status record\n"); 172 for (i = 0; i < 5 * 4 * 4; i += 16) { 173 memcpy(x, bp, 16); 174 bp += 4; 175 pr_notice("%03x: %08x %08x %08x %08x\n", 176 i, ntohl(x[0]), ntohl(x[1]), ntohl(x[2]), ntohl(x[3])); 177 } 178 179 memcpy(x, bp, 4); 180 pr_notice("0x50: %08x\n", ntohl(x[0])); 181 } 182 183 /* 184 * Decode a YFSFetchStatus block 185 */ 186 static int xdr_decode_YFSFetchStatus(struct afs_call *call, 187 const __be32 **_bp, 188 struct afs_file_status *status, 189 struct afs_vnode *vnode, 190 const afs_dataversion_t *expected_version, 191 struct afs_read *read_req) 192 { 193 const struct yfs_xdr_YFSFetchStatus *xdr = (const void *)*_bp; 194 u32 type; 195 u8 flags = 0; 196 197 status->abort_code = ntohl(xdr->abort_code); 198 if (status->abort_code != 0) { 199 if (vnode && status->abort_code == VNOVNODE) { 200 set_bit(AFS_VNODE_DELETED, &vnode->flags); 201 status->nlink = 0; 202 __afs_break_callback(vnode); 203 } 204 return 0; 205 } 206 207 type = ntohl(xdr->type); 208 switch (type) { 209 case AFS_FTYPE_FILE: 210 case AFS_FTYPE_DIR: 211 case AFS_FTYPE_SYMLINK: 212 if (type != status->type && 213 vnode && 214 !test_bit(AFS_VNODE_UNSET, &vnode->flags)) { 215 pr_warning("Vnode %llx:%llx:%x changed type %u to %u\n", 216 vnode->fid.vid, 217 vnode->fid.vnode, 218 vnode->fid.unique, 219 status->type, type); 220 goto bad; 221 } 222 status->type = type; 223 break; 224 default: 225 goto bad; 226 } 227 228 #define EXTRACT_M4(FIELD) \ 229 do { \ 230 u32 x = ntohl(xdr->FIELD); \ 231 if (status->FIELD != x) { \ 232 flags |= AFS_VNODE_META_CHANGED; \ 233 status->FIELD = x; \ 234 } \ 235 } while (0) 236 237 #define EXTRACT_M8(FIELD) \ 238 do { \ 239 u64 x = xdr_to_u64(xdr->FIELD); \ 240 if (status->FIELD != x) { \ 241 flags |= AFS_VNODE_META_CHANGED; \ 242 status->FIELD = x; \ 243 } \ 244 } while (0) 245 246 #define EXTRACT_D8(FIELD) \ 247 do { \ 248 u64 x = xdr_to_u64(xdr->FIELD); \ 249 if (status->FIELD != x) { \ 250 flags |= AFS_VNODE_DATA_CHANGED; \ 251 status->FIELD = x; \ 252 } \ 253 } while (0) 254 255 EXTRACT_M4(nlink); 256 EXTRACT_D8(size); 257 EXTRACT_D8(data_version); 258 EXTRACT_M8(author); 259 EXTRACT_M8(owner); 260 EXTRACT_M8(group); 261 EXTRACT_M4(mode); 262 EXTRACT_M4(caller_access); /* call ticket dependent */ 263 EXTRACT_M4(anon_access); 264 265 status->mtime_client = xdr_to_time(xdr->mtime_client); 266 status->mtime_server = xdr_to_time(xdr->mtime_server); 267 status->lock_count = ntohl(xdr->lock_count); 268 269 if (read_req) { 270 read_req->data_version = status->data_version; 271 read_req->file_size = status->size; 272 } 273 274 *_bp += xdr_size(xdr); 275 276 if (vnode) { 277 if (test_bit(AFS_VNODE_UNSET, &vnode->flags)) 278 flags |= AFS_VNODE_NOT_YET_SET; 279 afs_update_inode_from_status(vnode, status, expected_version, 280 flags); 281 } 282 283 return 0; 284 285 bad: 286 xdr_dump_bad(*_bp); 287 return afs_protocol_error(call, -EBADMSG, afs_eproto_bad_status); 288 } 289 290 /* 291 * Decode the file status. We need to lock the target vnode if we're going to 292 * update its status so that stat() sees the attributes update atomically. 293 */ 294 static int yfs_decode_status(struct afs_call *call, 295 const __be32 **_bp, 296 struct afs_file_status *status, 297 struct afs_vnode *vnode, 298 const afs_dataversion_t *expected_version, 299 struct afs_read *read_req) 300 { 301 int ret; 302 303 if (!vnode) 304 return xdr_decode_YFSFetchStatus(call, _bp, status, vnode, 305 expected_version, read_req); 306 307 write_seqlock(&vnode->cb_lock); 308 ret = xdr_decode_YFSFetchStatus(call, _bp, status, vnode, 309 expected_version, read_req); 310 write_sequnlock(&vnode->cb_lock); 311 return ret; 312 } 313 314 /* 315 * Decode a YFSCallBack block 316 */ 317 static void xdr_decode_YFSCallBack(struct afs_call *call, 318 struct afs_vnode *vnode, 319 const __be32 **_bp) 320 { 321 struct yfs_xdr_YFSCallBack *xdr = (void *)*_bp; 322 struct afs_cb_interest *old, *cbi = call->cbi; 323 u64 cb_expiry; 324 325 write_seqlock(&vnode->cb_lock); 326 327 if (!afs_cb_is_broken(call->cb_break, vnode, cbi)) { 328 cb_expiry = xdr_to_u64(xdr->expiration_time); 329 do_div(cb_expiry, 10 * 1000 * 1000); 330 vnode->cb_version = ntohl(xdr->version); 331 vnode->cb_type = ntohl(xdr->type); 332 vnode->cb_expires_at = cb_expiry + ktime_get_real_seconds(); 333 old = vnode->cb_interest; 334 if (old != call->cbi) { 335 vnode->cb_interest = cbi; 336 cbi = old; 337 } 338 set_bit(AFS_VNODE_CB_PROMISED, &vnode->flags); 339 } 340 341 write_sequnlock(&vnode->cb_lock); 342 call->cbi = cbi; 343 *_bp += xdr_size(xdr); 344 } 345 346 static void xdr_decode_YFSCallBack_raw(const __be32 **_bp, 347 struct afs_callback *cb) 348 { 349 struct yfs_xdr_YFSCallBack *x = (void *)*_bp; 350 u64 cb_expiry; 351 352 cb_expiry = xdr_to_u64(x->expiration_time); 353 do_div(cb_expiry, 10 * 1000 * 1000); 354 cb->version = ntohl(x->version); 355 cb->type = ntohl(x->type); 356 cb->expires_at = cb_expiry + ktime_get_real_seconds(); 357 358 *_bp += xdr_size(x); 359 } 360 361 /* 362 * Decode a YFSVolSync block 363 */ 364 static void xdr_decode_YFSVolSync(const __be32 **_bp, 365 struct afs_volsync *volsync) 366 { 367 struct yfs_xdr_YFSVolSync *x = (void *)*_bp; 368 u64 creation; 369 370 if (volsync) { 371 creation = xdr_to_u64(x->vol_creation_date); 372 do_div(creation, 10 * 1000 * 1000); 373 volsync->creation = creation; 374 } 375 376 *_bp += xdr_size(x); 377 } 378 379 /* 380 * Encode the requested attributes into a YFSStoreStatus block 381 */ 382 static __be32 *xdr_encode_YFS_StoreStatus(__be32 *bp, struct iattr *attr) 383 { 384 struct yfs_xdr_YFSStoreStatus *x = (void *)bp; 385 s64 mtime = 0, owner = 0, group = 0; 386 u32 mask = 0, mode = 0; 387 388 mask = 0; 389 if (attr->ia_valid & ATTR_MTIME) { 390 mask |= AFS_SET_MTIME; 391 mtime = linux_to_yfs_time(&attr->ia_mtime); 392 } 393 394 if (attr->ia_valid & ATTR_UID) { 395 mask |= AFS_SET_OWNER; 396 owner = from_kuid(&init_user_ns, attr->ia_uid); 397 } 398 399 if (attr->ia_valid & ATTR_GID) { 400 mask |= AFS_SET_GROUP; 401 group = from_kgid(&init_user_ns, attr->ia_gid); 402 } 403 404 if (attr->ia_valid & ATTR_MODE) { 405 mask |= AFS_SET_MODE; 406 mode = attr->ia_mode & S_IALLUGO; 407 } 408 409 x->mask = htonl(mask); 410 x->mode = htonl(mode); 411 x->mtime_client = u64_to_xdr(mtime); 412 x->owner = u64_to_xdr(owner); 413 x->group = u64_to_xdr(group); 414 return bp + xdr_size(x); 415 } 416 417 /* 418 * Decode a YFSFetchVolumeStatus block. 419 */ 420 static void xdr_decode_YFSFetchVolumeStatus(const __be32 **_bp, 421 struct afs_volume_status *vs) 422 { 423 const struct yfs_xdr_YFSFetchVolumeStatus *x = (const void *)*_bp; 424 u32 flags; 425 426 vs->vid = xdr_to_u64(x->vid); 427 vs->parent_id = xdr_to_u64(x->parent_id); 428 flags = ntohl(x->flags); 429 vs->online = flags & yfs_FVSOnline; 430 vs->in_service = flags & yfs_FVSInservice; 431 vs->blessed = flags & yfs_FVSBlessed; 432 vs->needs_salvage = flags & yfs_FVSNeedsSalvage; 433 vs->type = ntohl(x->type); 434 vs->min_quota = 0; 435 vs->max_quota = xdr_to_u64(x->max_quota); 436 vs->blocks_in_use = xdr_to_u64(x->blocks_in_use); 437 vs->part_blocks_avail = xdr_to_u64(x->part_blocks_avail); 438 vs->part_max_blocks = xdr_to_u64(x->part_max_blocks); 439 vs->vol_copy_date = xdr_to_u64(x->vol_copy_date); 440 vs->vol_backup_date = xdr_to_u64(x->vol_backup_date); 441 *_bp += sizeof(*x) / sizeof(__be32); 442 } 443 444 /* 445 * deliver reply data to an FS.FetchStatus 446 */ 447 static int yfs_deliver_fs_fetch_status_vnode(struct afs_call *call) 448 { 449 struct afs_vnode *vnode = call->reply[0]; 450 const __be32 *bp; 451 int ret; 452 453 ret = afs_transfer_reply(call); 454 if (ret < 0) 455 return ret; 456 457 _enter("{%llx:%llu}", vnode->fid.vid, vnode->fid.vnode); 458 459 /* unmarshall the reply once we've received all of it */ 460 bp = call->buffer; 461 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, 462 &call->expected_version, NULL); 463 if (ret < 0) 464 return ret; 465 xdr_decode_YFSCallBack(call, vnode, &bp); 466 xdr_decode_YFSVolSync(&bp, call->reply[1]); 467 468 _leave(" = 0 [done]"); 469 return 0; 470 } 471 472 /* 473 * YFS.FetchStatus operation type 474 */ 475 static const struct afs_call_type yfs_RXYFSFetchStatus_vnode = { 476 .name = "YFS.FetchStatus(vnode)", 477 .op = yfs_FS_FetchStatus, 478 .deliver = yfs_deliver_fs_fetch_status_vnode, 479 .destructor = afs_flat_call_destructor, 480 }; 481 482 /* 483 * Fetch the status information for a file. 484 */ 485 int yfs_fs_fetch_file_status(struct afs_fs_cursor *fc, struct afs_volsync *volsync, 486 bool new_inode) 487 { 488 struct afs_vnode *vnode = fc->vnode; 489 struct afs_call *call; 490 struct afs_net *net = afs_v2net(vnode); 491 __be32 *bp; 492 493 _enter(",%x,{%llx:%llu},,", 494 key_serial(fc->key), vnode->fid.vid, vnode->fid.vnode); 495 496 call = afs_alloc_flat_call(net, &yfs_RXYFSFetchStatus_vnode, 497 sizeof(__be32) * 2 + 498 sizeof(struct yfs_xdr_YFSFid), 499 sizeof(struct yfs_xdr_YFSFetchStatus) + 500 sizeof(struct yfs_xdr_YFSCallBack) + 501 sizeof(struct yfs_xdr_YFSVolSync)); 502 if (!call) { 503 fc->ac.error = -ENOMEM; 504 return -ENOMEM; 505 } 506 507 call->key = fc->key; 508 call->reply[0] = vnode; 509 call->reply[1] = volsync; 510 call->expected_version = new_inode ? 1 : vnode->status.data_version; 511 512 /* marshall the parameters */ 513 bp = call->request; 514 bp = xdr_encode_u32(bp, YFSFETCHSTATUS); 515 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 516 bp = xdr_encode_YFSFid(bp, &vnode->fid); 517 yfs_check_req(call, bp); 518 519 call->cb_break = fc->cb_break; 520 afs_use_fs_server(call, fc->cbi); 521 trace_afs_make_fs_call(call, &vnode->fid); 522 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 523 } 524 525 /* 526 * Deliver reply data to an YFS.FetchData64. 527 */ 528 static int yfs_deliver_fs_fetch_data64(struct afs_call *call) 529 { 530 struct afs_vnode *vnode = call->reply[0]; 531 struct afs_read *req = call->reply[2]; 532 const __be32 *bp; 533 unsigned int size; 534 int ret; 535 536 _enter("{%u,%zu/%llu}", 537 call->unmarshall, iov_iter_count(&call->iter), req->actual_len); 538 539 switch (call->unmarshall) { 540 case 0: 541 req->actual_len = 0; 542 req->index = 0; 543 req->offset = req->pos & (PAGE_SIZE - 1); 544 afs_extract_to_tmp64(call); 545 call->unmarshall++; 546 547 /* extract the returned data length */ 548 case 1: 549 _debug("extract data length"); 550 ret = afs_extract_data(call, true); 551 if (ret < 0) 552 return ret; 553 554 req->actual_len = be64_to_cpu(call->tmp64); 555 _debug("DATA length: %llu", req->actual_len); 556 req->remain = min(req->len, req->actual_len); 557 if (req->remain == 0) 558 goto no_more_data; 559 560 call->unmarshall++; 561 562 begin_page: 563 ASSERTCMP(req->index, <, req->nr_pages); 564 if (req->remain > PAGE_SIZE - req->offset) 565 size = PAGE_SIZE - req->offset; 566 else 567 size = req->remain; 568 call->bvec[0].bv_len = size; 569 call->bvec[0].bv_offset = req->offset; 570 call->bvec[0].bv_page = req->pages[req->index]; 571 iov_iter_bvec(&call->iter, READ, call->bvec, 1, size); 572 ASSERTCMP(size, <=, PAGE_SIZE); 573 574 /* extract the returned data */ 575 case 2: 576 _debug("extract data %zu/%llu", 577 iov_iter_count(&call->iter), req->remain); 578 579 ret = afs_extract_data(call, true); 580 if (ret < 0) 581 return ret; 582 req->remain -= call->bvec[0].bv_len; 583 req->offset += call->bvec[0].bv_len; 584 ASSERTCMP(req->offset, <=, PAGE_SIZE); 585 if (req->offset == PAGE_SIZE) { 586 req->offset = 0; 587 if (req->page_done) 588 req->page_done(call, req); 589 req->index++; 590 if (req->remain > 0) 591 goto begin_page; 592 } 593 594 ASSERTCMP(req->remain, ==, 0); 595 if (req->actual_len <= req->len) 596 goto no_more_data; 597 598 /* Discard any excess data the server gave us */ 599 iov_iter_discard(&call->iter, READ, req->actual_len - req->len); 600 call->unmarshall = 3; 601 case 3: 602 _debug("extract discard %zu/%llu", 603 iov_iter_count(&call->iter), req->actual_len - req->len); 604 605 ret = afs_extract_data(call, true); 606 if (ret < 0) 607 return ret; 608 609 no_more_data: 610 call->unmarshall = 4; 611 afs_extract_to_buf(call, 612 sizeof(struct yfs_xdr_YFSFetchStatus) + 613 sizeof(struct yfs_xdr_YFSCallBack) + 614 sizeof(struct yfs_xdr_YFSVolSync)); 615 616 /* extract the metadata */ 617 case 4: 618 ret = afs_extract_data(call, false); 619 if (ret < 0) 620 return ret; 621 622 bp = call->buffer; 623 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, 624 &vnode->status.data_version, req); 625 if (ret < 0) 626 return ret; 627 xdr_decode_YFSCallBack(call, vnode, &bp); 628 xdr_decode_YFSVolSync(&bp, call->reply[1]); 629 630 call->unmarshall++; 631 632 case 5: 633 break; 634 } 635 636 for (; req->index < req->nr_pages; req->index++) { 637 if (req->offset < PAGE_SIZE) 638 zero_user_segment(req->pages[req->index], 639 req->offset, PAGE_SIZE); 640 if (req->page_done) 641 req->page_done(call, req); 642 req->offset = 0; 643 } 644 645 _leave(" = 0 [done]"); 646 return 0; 647 } 648 649 static void yfs_fetch_data_destructor(struct afs_call *call) 650 { 651 struct afs_read *req = call->reply[2]; 652 653 afs_put_read(req); 654 afs_flat_call_destructor(call); 655 } 656 657 /* 658 * YFS.FetchData64 operation type 659 */ 660 static const struct afs_call_type yfs_RXYFSFetchData64 = { 661 .name = "YFS.FetchData64", 662 .op = yfs_FS_FetchData64, 663 .deliver = yfs_deliver_fs_fetch_data64, 664 .destructor = yfs_fetch_data_destructor, 665 }; 666 667 /* 668 * Fetch data from a file. 669 */ 670 int yfs_fs_fetch_data(struct afs_fs_cursor *fc, struct afs_read *req) 671 { 672 struct afs_vnode *vnode = fc->vnode; 673 struct afs_call *call; 674 struct afs_net *net = afs_v2net(vnode); 675 __be32 *bp; 676 677 _enter(",%x,{%llx:%llu},%llx,%llx", 678 key_serial(fc->key), vnode->fid.vid, vnode->fid.vnode, 679 req->pos, req->len); 680 681 call = afs_alloc_flat_call(net, &yfs_RXYFSFetchData64, 682 sizeof(__be32) * 2 + 683 sizeof(struct yfs_xdr_YFSFid) + 684 sizeof(struct yfs_xdr_u64) * 2, 685 sizeof(struct yfs_xdr_YFSFetchStatus) + 686 sizeof(struct yfs_xdr_YFSCallBack) + 687 sizeof(struct yfs_xdr_YFSVolSync)); 688 if (!call) 689 return -ENOMEM; 690 691 call->key = fc->key; 692 call->reply[0] = vnode; 693 call->reply[1] = NULL; /* volsync */ 694 call->reply[2] = req; 695 call->expected_version = vnode->status.data_version; 696 call->want_reply_time = true; 697 698 /* marshall the parameters */ 699 bp = call->request; 700 bp = xdr_encode_u32(bp, YFSFETCHDATA64); 701 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 702 bp = xdr_encode_YFSFid(bp, &vnode->fid); 703 bp = xdr_encode_u64(bp, req->pos); 704 bp = xdr_encode_u64(bp, req->len); 705 yfs_check_req(call, bp); 706 707 refcount_inc(&req->usage); 708 call->cb_break = fc->cb_break; 709 afs_use_fs_server(call, fc->cbi); 710 trace_afs_make_fs_call(call, &vnode->fid); 711 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 712 } 713 714 /* 715 * Deliver reply data for YFS.CreateFile or YFS.MakeDir. 716 */ 717 static int yfs_deliver_fs_create_vnode(struct afs_call *call) 718 { 719 struct afs_vnode *vnode = call->reply[0]; 720 const __be32 *bp; 721 int ret; 722 723 _enter("{%u}", call->unmarshall); 724 725 ret = afs_transfer_reply(call); 726 if (ret < 0) 727 return ret; 728 729 /* unmarshall the reply once we've received all of it */ 730 bp = call->buffer; 731 xdr_decode_YFSFid(&bp, call->reply[1]); 732 ret = yfs_decode_status(call, &bp, call->reply[2], NULL, NULL, NULL); 733 if (ret < 0) 734 return ret; 735 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, 736 &call->expected_version, NULL); 737 if (ret < 0) 738 return ret; 739 xdr_decode_YFSCallBack_raw(&bp, call->reply[3]); 740 xdr_decode_YFSVolSync(&bp, NULL); 741 742 _leave(" = 0 [done]"); 743 return 0; 744 } 745 746 /* 747 * FS.CreateFile and FS.MakeDir operation type 748 */ 749 static const struct afs_call_type afs_RXFSCreateFile = { 750 .name = "YFS.CreateFile", 751 .op = yfs_FS_CreateFile, 752 .deliver = yfs_deliver_fs_create_vnode, 753 .destructor = afs_flat_call_destructor, 754 }; 755 756 /* 757 * Create a file. 758 */ 759 int yfs_fs_create_file(struct afs_fs_cursor *fc, 760 const char *name, 761 umode_t mode, 762 u64 current_data_version, 763 struct afs_fid *newfid, 764 struct afs_file_status *newstatus, 765 struct afs_callback *newcb) 766 { 767 struct afs_vnode *vnode = fc->vnode; 768 struct afs_call *call; 769 struct afs_net *net = afs_v2net(vnode); 770 size_t namesz, reqsz, rplsz; 771 __be32 *bp; 772 773 _enter(""); 774 775 namesz = strlen(name); 776 reqsz = (sizeof(__be32) + 777 sizeof(__be32) + 778 sizeof(struct yfs_xdr_YFSFid) + 779 xdr_strlen(namesz) + 780 sizeof(struct yfs_xdr_YFSStoreStatus) + 781 sizeof(__be32)); 782 rplsz = (sizeof(struct yfs_xdr_YFSFid) + 783 sizeof(struct yfs_xdr_YFSFetchStatus) + 784 sizeof(struct yfs_xdr_YFSFetchStatus) + 785 sizeof(struct yfs_xdr_YFSCallBack) + 786 sizeof(struct yfs_xdr_YFSVolSync)); 787 788 call = afs_alloc_flat_call(net, &afs_RXFSCreateFile, reqsz, rplsz); 789 if (!call) 790 return -ENOMEM; 791 792 call->key = fc->key; 793 call->reply[0] = vnode; 794 call->reply[1] = newfid; 795 call->reply[2] = newstatus; 796 call->reply[3] = newcb; 797 call->expected_version = current_data_version + 1; 798 799 /* marshall the parameters */ 800 bp = call->request; 801 bp = xdr_encode_u32(bp, YFSCREATEFILE); 802 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 803 bp = xdr_encode_YFSFid(bp, &vnode->fid); 804 bp = xdr_encode_string(bp, name, namesz); 805 bp = xdr_encode_YFSStoreStatus_mode(bp, mode); 806 bp = xdr_encode_u32(bp, 0); /* ViceLockType */ 807 yfs_check_req(call, bp); 808 809 afs_use_fs_server(call, fc->cbi); 810 trace_afs_make_fs_call(call, &vnode->fid); 811 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 812 } 813 814 static const struct afs_call_type yfs_RXFSMakeDir = { 815 .name = "YFS.MakeDir", 816 .op = yfs_FS_MakeDir, 817 .deliver = yfs_deliver_fs_create_vnode, 818 .destructor = afs_flat_call_destructor, 819 }; 820 821 /* 822 * Make a directory. 823 */ 824 int yfs_fs_make_dir(struct afs_fs_cursor *fc, 825 const char *name, 826 umode_t mode, 827 u64 current_data_version, 828 struct afs_fid *newfid, 829 struct afs_file_status *newstatus, 830 struct afs_callback *newcb) 831 { 832 struct afs_vnode *vnode = fc->vnode; 833 struct afs_call *call; 834 struct afs_net *net = afs_v2net(vnode); 835 size_t namesz, reqsz, rplsz; 836 __be32 *bp; 837 838 _enter(""); 839 840 namesz = strlen(name); 841 reqsz = (sizeof(__be32) + 842 sizeof(struct yfs_xdr_RPCFlags) + 843 sizeof(struct yfs_xdr_YFSFid) + 844 xdr_strlen(namesz) + 845 sizeof(struct yfs_xdr_YFSStoreStatus)); 846 rplsz = (sizeof(struct yfs_xdr_YFSFid) + 847 sizeof(struct yfs_xdr_YFSFetchStatus) + 848 sizeof(struct yfs_xdr_YFSFetchStatus) + 849 sizeof(struct yfs_xdr_YFSCallBack) + 850 sizeof(struct yfs_xdr_YFSVolSync)); 851 852 call = afs_alloc_flat_call(net, &yfs_RXFSMakeDir, reqsz, rplsz); 853 if (!call) 854 return -ENOMEM; 855 856 call->key = fc->key; 857 call->reply[0] = vnode; 858 call->reply[1] = newfid; 859 call->reply[2] = newstatus; 860 call->reply[3] = newcb; 861 call->expected_version = current_data_version + 1; 862 863 /* marshall the parameters */ 864 bp = call->request; 865 bp = xdr_encode_u32(bp, YFSMAKEDIR); 866 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 867 bp = xdr_encode_YFSFid(bp, &vnode->fid); 868 bp = xdr_encode_string(bp, name, namesz); 869 bp = xdr_encode_YFSStoreStatus_mode(bp, mode); 870 yfs_check_req(call, bp); 871 872 afs_use_fs_server(call, fc->cbi); 873 trace_afs_make_fs_call(call, &vnode->fid); 874 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 875 } 876 877 /* 878 * Deliver reply data to a YFS.RemoveFile2 operation. 879 */ 880 static int yfs_deliver_fs_remove_file2(struct afs_call *call) 881 { 882 struct afs_vnode *dvnode = call->reply[0]; 883 struct afs_vnode *vnode = call->reply[1]; 884 struct afs_fid fid; 885 const __be32 *bp; 886 int ret; 887 888 _enter("{%u}", call->unmarshall); 889 890 ret = afs_transfer_reply(call); 891 if (ret < 0) 892 return ret; 893 894 /* unmarshall the reply once we've received all of it */ 895 bp = call->buffer; 896 ret = yfs_decode_status(call, &bp, &dvnode->status, dvnode, 897 &call->expected_version, NULL); 898 if (ret < 0) 899 return ret; 900 901 xdr_decode_YFSFid(&bp, &fid); 902 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, NULL, NULL); 903 if (ret < 0) 904 return ret; 905 /* Was deleted if vnode->status.abort_code == VNOVNODE. */ 906 907 xdr_decode_YFSVolSync(&bp, NULL); 908 return 0; 909 } 910 911 /* 912 * YFS.RemoveFile2 operation type. 913 */ 914 static const struct afs_call_type yfs_RXYFSRemoveFile2 = { 915 .name = "YFS.RemoveFile2", 916 .op = yfs_FS_RemoveFile2, 917 .deliver = yfs_deliver_fs_remove_file2, 918 .destructor = afs_flat_call_destructor, 919 }; 920 921 /* 922 * Remove a file and retrieve new file status. 923 */ 924 int yfs_fs_remove_file2(struct afs_fs_cursor *fc, struct afs_vnode *vnode, 925 const char *name, u64 current_data_version) 926 { 927 struct afs_vnode *dvnode = fc->vnode; 928 struct afs_call *call; 929 struct afs_net *net = afs_v2net(dvnode); 930 size_t namesz; 931 __be32 *bp; 932 933 _enter(""); 934 935 namesz = strlen(name); 936 937 call = afs_alloc_flat_call(net, &yfs_RXYFSRemoveFile2, 938 sizeof(__be32) + 939 sizeof(struct yfs_xdr_RPCFlags) + 940 sizeof(struct yfs_xdr_YFSFid) + 941 xdr_strlen(namesz), 942 sizeof(struct yfs_xdr_YFSFetchStatus) + 943 sizeof(struct yfs_xdr_YFSFid) + 944 sizeof(struct yfs_xdr_YFSFetchStatus) + 945 sizeof(struct yfs_xdr_YFSVolSync)); 946 if (!call) 947 return -ENOMEM; 948 949 call->key = fc->key; 950 call->reply[0] = dvnode; 951 call->reply[1] = vnode; 952 call->expected_version = current_data_version + 1; 953 954 /* marshall the parameters */ 955 bp = call->request; 956 bp = xdr_encode_u32(bp, YFSREMOVEFILE2); 957 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 958 bp = xdr_encode_YFSFid(bp, &dvnode->fid); 959 bp = xdr_encode_string(bp, name, namesz); 960 yfs_check_req(call, bp); 961 962 afs_use_fs_server(call, fc->cbi); 963 trace_afs_make_fs_call(call, &dvnode->fid); 964 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 965 } 966 967 /* 968 * Deliver reply data to a YFS.RemoveFile or YFS.RemoveDir operation. 969 */ 970 static int yfs_deliver_fs_remove(struct afs_call *call) 971 { 972 struct afs_vnode *dvnode = call->reply[0]; 973 const __be32 *bp; 974 int ret; 975 976 _enter("{%u}", call->unmarshall); 977 978 ret = afs_transfer_reply(call); 979 if (ret < 0) 980 return ret; 981 982 /* unmarshall the reply once we've received all of it */ 983 bp = call->buffer; 984 ret = yfs_decode_status(call, &bp, &dvnode->status, dvnode, 985 &call->expected_version, NULL); 986 if (ret < 0) 987 return ret; 988 989 xdr_decode_YFSVolSync(&bp, NULL); 990 return 0; 991 } 992 993 /* 994 * FS.RemoveDir and FS.RemoveFile operation types. 995 */ 996 static const struct afs_call_type yfs_RXYFSRemoveFile = { 997 .name = "YFS.RemoveFile", 998 .op = yfs_FS_RemoveFile, 999 .deliver = yfs_deliver_fs_remove, 1000 .destructor = afs_flat_call_destructor, 1001 }; 1002 1003 static const struct afs_call_type yfs_RXYFSRemoveDir = { 1004 .name = "YFS.RemoveDir", 1005 .op = yfs_FS_RemoveDir, 1006 .deliver = yfs_deliver_fs_remove, 1007 .destructor = afs_flat_call_destructor, 1008 }; 1009 1010 /* 1011 * remove a file or directory 1012 */ 1013 int yfs_fs_remove(struct afs_fs_cursor *fc, struct afs_vnode *vnode, 1014 const char *name, bool isdir, u64 current_data_version) 1015 { 1016 struct afs_vnode *dvnode = fc->vnode; 1017 struct afs_call *call; 1018 struct afs_net *net = afs_v2net(dvnode); 1019 size_t namesz; 1020 __be32 *bp; 1021 1022 _enter(""); 1023 1024 namesz = strlen(name); 1025 call = afs_alloc_flat_call( 1026 net, isdir ? &yfs_RXYFSRemoveDir : &yfs_RXYFSRemoveFile, 1027 sizeof(__be32) + 1028 sizeof(struct yfs_xdr_RPCFlags) + 1029 sizeof(struct yfs_xdr_YFSFid) + 1030 xdr_strlen(namesz), 1031 sizeof(struct yfs_xdr_YFSFetchStatus) + 1032 sizeof(struct yfs_xdr_YFSVolSync)); 1033 if (!call) 1034 return -ENOMEM; 1035 1036 call->key = fc->key; 1037 call->reply[0] = dvnode; 1038 call->reply[1] = vnode; 1039 call->expected_version = current_data_version + 1; 1040 1041 /* marshall the parameters */ 1042 bp = call->request; 1043 bp = xdr_encode_u32(bp, isdir ? YFSREMOVEDIR : YFSREMOVEFILE); 1044 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1045 bp = xdr_encode_YFSFid(bp, &dvnode->fid); 1046 bp = xdr_encode_string(bp, name, namesz); 1047 yfs_check_req(call, bp); 1048 1049 afs_use_fs_server(call, fc->cbi); 1050 trace_afs_make_fs_call(call, &dvnode->fid); 1051 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1052 } 1053 1054 /* 1055 * Deliver reply data to a YFS.Link operation. 1056 */ 1057 static int yfs_deliver_fs_link(struct afs_call *call) 1058 { 1059 struct afs_vnode *dvnode = call->reply[0], *vnode = call->reply[1]; 1060 const __be32 *bp; 1061 int ret; 1062 1063 _enter("{%u}", call->unmarshall); 1064 1065 ret = afs_transfer_reply(call); 1066 if (ret < 0) 1067 return ret; 1068 1069 /* unmarshall the reply once we've received all of it */ 1070 bp = call->buffer; 1071 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, NULL, NULL); 1072 if (ret < 0) 1073 return ret; 1074 ret = yfs_decode_status(call, &bp, &dvnode->status, dvnode, 1075 &call->expected_version, NULL); 1076 if (ret < 0) 1077 return ret; 1078 xdr_decode_YFSVolSync(&bp, NULL); 1079 _leave(" = 0 [done]"); 1080 return 0; 1081 } 1082 1083 /* 1084 * YFS.Link operation type. 1085 */ 1086 static const struct afs_call_type yfs_RXYFSLink = { 1087 .name = "YFS.Link", 1088 .op = yfs_FS_Link, 1089 .deliver = yfs_deliver_fs_link, 1090 .destructor = afs_flat_call_destructor, 1091 }; 1092 1093 /* 1094 * Make a hard link. 1095 */ 1096 int yfs_fs_link(struct afs_fs_cursor *fc, struct afs_vnode *vnode, 1097 const char *name, u64 current_data_version) 1098 { 1099 struct afs_vnode *dvnode = fc->vnode; 1100 struct afs_call *call; 1101 struct afs_net *net = afs_v2net(vnode); 1102 size_t namesz; 1103 __be32 *bp; 1104 1105 _enter(""); 1106 1107 namesz = strlen(name); 1108 call = afs_alloc_flat_call(net, &yfs_RXYFSLink, 1109 sizeof(__be32) + 1110 sizeof(struct yfs_xdr_RPCFlags) + 1111 sizeof(struct yfs_xdr_YFSFid) + 1112 xdr_strlen(namesz) + 1113 sizeof(struct yfs_xdr_YFSFid), 1114 sizeof(struct yfs_xdr_YFSFetchStatus) + 1115 sizeof(struct yfs_xdr_YFSFetchStatus) + 1116 sizeof(struct yfs_xdr_YFSVolSync)); 1117 if (!call) 1118 return -ENOMEM; 1119 1120 call->key = fc->key; 1121 call->reply[0] = dvnode; 1122 call->reply[1] = vnode; 1123 call->expected_version = current_data_version + 1; 1124 1125 /* marshall the parameters */ 1126 bp = call->request; 1127 bp = xdr_encode_u32(bp, YFSLINK); 1128 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1129 bp = xdr_encode_YFSFid(bp, &dvnode->fid); 1130 bp = xdr_encode_string(bp, name, namesz); 1131 bp = xdr_encode_YFSFid(bp, &vnode->fid); 1132 yfs_check_req(call, bp); 1133 1134 afs_use_fs_server(call, fc->cbi); 1135 trace_afs_make_fs_call(call, &vnode->fid); 1136 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1137 } 1138 1139 /* 1140 * Deliver reply data to a YFS.Symlink operation. 1141 */ 1142 static int yfs_deliver_fs_symlink(struct afs_call *call) 1143 { 1144 struct afs_vnode *vnode = call->reply[0]; 1145 const __be32 *bp; 1146 int ret; 1147 1148 _enter("{%u}", call->unmarshall); 1149 1150 ret = afs_transfer_reply(call); 1151 if (ret < 0) 1152 return ret; 1153 1154 /* unmarshall the reply once we've received all of it */ 1155 bp = call->buffer; 1156 xdr_decode_YFSFid(&bp, call->reply[1]); 1157 ret = yfs_decode_status(call, &bp, call->reply[2], NULL, NULL, NULL); 1158 if (ret < 0) 1159 return ret; 1160 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, 1161 &call->expected_version, NULL); 1162 if (ret < 0) 1163 return ret; 1164 xdr_decode_YFSVolSync(&bp, NULL); 1165 1166 _leave(" = 0 [done]"); 1167 return 0; 1168 } 1169 1170 /* 1171 * YFS.Symlink operation type 1172 */ 1173 static const struct afs_call_type yfs_RXYFSSymlink = { 1174 .name = "YFS.Symlink", 1175 .op = yfs_FS_Symlink, 1176 .deliver = yfs_deliver_fs_symlink, 1177 .destructor = afs_flat_call_destructor, 1178 }; 1179 1180 /* 1181 * Create a symbolic link. 1182 */ 1183 int yfs_fs_symlink(struct afs_fs_cursor *fc, 1184 const char *name, 1185 const char *contents, 1186 u64 current_data_version, 1187 struct afs_fid *newfid, 1188 struct afs_file_status *newstatus) 1189 { 1190 struct afs_vnode *dvnode = fc->vnode; 1191 struct afs_call *call; 1192 struct afs_net *net = afs_v2net(dvnode); 1193 size_t namesz, contents_sz; 1194 __be32 *bp; 1195 1196 _enter(""); 1197 1198 namesz = strlen(name); 1199 contents_sz = strlen(contents); 1200 call = afs_alloc_flat_call(net, &yfs_RXYFSSymlink, 1201 sizeof(__be32) + 1202 sizeof(struct yfs_xdr_RPCFlags) + 1203 sizeof(struct yfs_xdr_YFSFid) + 1204 xdr_strlen(namesz) + 1205 xdr_strlen(contents_sz) + 1206 sizeof(struct yfs_xdr_YFSStoreStatus), 1207 sizeof(struct yfs_xdr_YFSFid) + 1208 sizeof(struct yfs_xdr_YFSFetchStatus) + 1209 sizeof(struct yfs_xdr_YFSFetchStatus) + 1210 sizeof(struct yfs_xdr_YFSVolSync)); 1211 if (!call) 1212 return -ENOMEM; 1213 1214 call->key = fc->key; 1215 call->reply[0] = dvnode; 1216 call->reply[1] = newfid; 1217 call->reply[2] = newstatus; 1218 call->expected_version = current_data_version + 1; 1219 1220 /* marshall the parameters */ 1221 bp = call->request; 1222 bp = xdr_encode_u32(bp, YFSSYMLINK); 1223 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1224 bp = xdr_encode_YFSFid(bp, &dvnode->fid); 1225 bp = xdr_encode_string(bp, name, namesz); 1226 bp = xdr_encode_string(bp, contents, contents_sz); 1227 bp = xdr_encode_YFSStoreStatus_mode(bp, S_IRWXUGO); 1228 yfs_check_req(call, bp); 1229 1230 afs_use_fs_server(call, fc->cbi); 1231 trace_afs_make_fs_call(call, &dvnode->fid); 1232 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1233 } 1234 1235 /* 1236 * Deliver reply data to a YFS.Rename operation. 1237 */ 1238 static int yfs_deliver_fs_rename(struct afs_call *call) 1239 { 1240 struct afs_vnode *orig_dvnode = call->reply[0]; 1241 struct afs_vnode *new_dvnode = call->reply[1]; 1242 const __be32 *bp; 1243 int ret; 1244 1245 _enter("{%u}", call->unmarshall); 1246 1247 ret = afs_transfer_reply(call); 1248 if (ret < 0) 1249 return ret; 1250 1251 /* unmarshall the reply once we've received all of it */ 1252 bp = call->buffer; 1253 ret = yfs_decode_status(call, &bp, &orig_dvnode->status, orig_dvnode, 1254 &call->expected_version, NULL); 1255 if (ret < 0) 1256 return ret; 1257 if (new_dvnode != orig_dvnode) { 1258 ret = yfs_decode_status(call, &bp, &new_dvnode->status, new_dvnode, 1259 &call->expected_version_2, NULL); 1260 if (ret < 0) 1261 return ret; 1262 } 1263 1264 xdr_decode_YFSVolSync(&bp, NULL); 1265 _leave(" = 0 [done]"); 1266 return 0; 1267 } 1268 1269 /* 1270 * YFS.Rename operation type 1271 */ 1272 static const struct afs_call_type yfs_RXYFSRename = { 1273 .name = "FS.Rename", 1274 .op = yfs_FS_Rename, 1275 .deliver = yfs_deliver_fs_rename, 1276 .destructor = afs_flat_call_destructor, 1277 }; 1278 1279 /* 1280 * Rename a file or directory. 1281 */ 1282 int yfs_fs_rename(struct afs_fs_cursor *fc, 1283 const char *orig_name, 1284 struct afs_vnode *new_dvnode, 1285 const char *new_name, 1286 u64 current_orig_data_version, 1287 u64 current_new_data_version) 1288 { 1289 struct afs_vnode *orig_dvnode = fc->vnode; 1290 struct afs_call *call; 1291 struct afs_net *net = afs_v2net(orig_dvnode); 1292 size_t o_namesz, n_namesz; 1293 __be32 *bp; 1294 1295 _enter(""); 1296 1297 o_namesz = strlen(orig_name); 1298 n_namesz = strlen(new_name); 1299 call = afs_alloc_flat_call(net, &yfs_RXYFSRename, 1300 sizeof(__be32) + 1301 sizeof(struct yfs_xdr_RPCFlags) + 1302 sizeof(struct yfs_xdr_YFSFid) + 1303 xdr_strlen(o_namesz) + 1304 sizeof(struct yfs_xdr_YFSFid) + 1305 xdr_strlen(n_namesz), 1306 sizeof(struct yfs_xdr_YFSFetchStatus) + 1307 sizeof(struct yfs_xdr_YFSFetchStatus) + 1308 sizeof(struct yfs_xdr_YFSVolSync)); 1309 if (!call) 1310 return -ENOMEM; 1311 1312 call->key = fc->key; 1313 call->reply[0] = orig_dvnode; 1314 call->reply[1] = new_dvnode; 1315 call->expected_version = current_orig_data_version + 1; 1316 call->expected_version_2 = current_new_data_version + 1; 1317 1318 /* marshall the parameters */ 1319 bp = call->request; 1320 bp = xdr_encode_u32(bp, YFSRENAME); 1321 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1322 bp = xdr_encode_YFSFid(bp, &orig_dvnode->fid); 1323 bp = xdr_encode_string(bp, orig_name, o_namesz); 1324 bp = xdr_encode_YFSFid(bp, &new_dvnode->fid); 1325 bp = xdr_encode_string(bp, new_name, n_namesz); 1326 yfs_check_req(call, bp); 1327 1328 afs_use_fs_server(call, fc->cbi); 1329 trace_afs_make_fs_call(call, &orig_dvnode->fid); 1330 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1331 } 1332 1333 /* 1334 * Deliver reply data to a YFS.StoreData64 operation. 1335 */ 1336 static int yfs_deliver_fs_store_data(struct afs_call *call) 1337 { 1338 struct afs_vnode *vnode = call->reply[0]; 1339 const __be32 *bp; 1340 int ret; 1341 1342 _enter(""); 1343 1344 ret = afs_transfer_reply(call); 1345 if (ret < 0) 1346 return ret; 1347 1348 /* unmarshall the reply once we've received all of it */ 1349 bp = call->buffer; 1350 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, 1351 &call->expected_version, NULL); 1352 if (ret < 0) 1353 return ret; 1354 xdr_decode_YFSVolSync(&bp, NULL); 1355 1356 afs_pages_written_back(vnode, call); 1357 1358 _leave(" = 0 [done]"); 1359 return 0; 1360 } 1361 1362 /* 1363 * YFS.StoreData64 operation type. 1364 */ 1365 static const struct afs_call_type yfs_RXYFSStoreData64 = { 1366 .name = "YFS.StoreData64", 1367 .op = yfs_FS_StoreData64, 1368 .deliver = yfs_deliver_fs_store_data, 1369 .destructor = afs_flat_call_destructor, 1370 }; 1371 1372 /* 1373 * Store a set of pages to a large file. 1374 */ 1375 int yfs_fs_store_data(struct afs_fs_cursor *fc, struct address_space *mapping, 1376 pgoff_t first, pgoff_t last, 1377 unsigned offset, unsigned to) 1378 { 1379 struct afs_vnode *vnode = fc->vnode; 1380 struct afs_call *call; 1381 struct afs_net *net = afs_v2net(vnode); 1382 loff_t size, pos, i_size; 1383 __be32 *bp; 1384 1385 _enter(",%x,{%llx:%llu},,", 1386 key_serial(fc->key), vnode->fid.vid, vnode->fid.vnode); 1387 1388 size = (loff_t)to - (loff_t)offset; 1389 if (first != last) 1390 size += (loff_t)(last - first) << PAGE_SHIFT; 1391 pos = (loff_t)first << PAGE_SHIFT; 1392 pos += offset; 1393 1394 i_size = i_size_read(&vnode->vfs_inode); 1395 if (pos + size > i_size) 1396 i_size = size + pos; 1397 1398 _debug("size %llx, at %llx, i_size %llx", 1399 (unsigned long long)size, (unsigned long long)pos, 1400 (unsigned long long)i_size); 1401 1402 call = afs_alloc_flat_call(net, &yfs_RXYFSStoreData64, 1403 sizeof(__be32) + 1404 sizeof(__be32) + 1405 sizeof(struct yfs_xdr_YFSFid) + 1406 sizeof(struct yfs_xdr_YFSStoreStatus) + 1407 sizeof(struct yfs_xdr_u64) * 3, 1408 sizeof(struct yfs_xdr_YFSFetchStatus) + 1409 sizeof(struct yfs_xdr_YFSVolSync)); 1410 if (!call) 1411 return -ENOMEM; 1412 1413 call->key = fc->key; 1414 call->mapping = mapping; 1415 call->reply[0] = vnode; 1416 call->first = first; 1417 call->last = last; 1418 call->first_offset = offset; 1419 call->last_to = to; 1420 call->send_pages = true; 1421 call->expected_version = vnode->status.data_version + 1; 1422 1423 /* marshall the parameters */ 1424 bp = call->request; 1425 bp = xdr_encode_u32(bp, YFSSTOREDATA64); 1426 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1427 bp = xdr_encode_YFSFid(bp, &vnode->fid); 1428 bp = xdr_encode_YFSStoreStatus_mtime(bp, &vnode->vfs_inode.i_mtime); 1429 bp = xdr_encode_u64(bp, pos); 1430 bp = xdr_encode_u64(bp, size); 1431 bp = xdr_encode_u64(bp, i_size); 1432 yfs_check_req(call, bp); 1433 1434 afs_use_fs_server(call, fc->cbi); 1435 trace_afs_make_fs_call(call, &vnode->fid); 1436 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1437 } 1438 1439 /* 1440 * deliver reply data to an FS.StoreStatus 1441 */ 1442 static int yfs_deliver_fs_store_status(struct afs_call *call) 1443 { 1444 struct afs_vnode *vnode = call->reply[0]; 1445 const __be32 *bp; 1446 int ret; 1447 1448 _enter(""); 1449 1450 ret = afs_transfer_reply(call); 1451 if (ret < 0) 1452 return ret; 1453 1454 /* unmarshall the reply once we've received all of it */ 1455 bp = call->buffer; 1456 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, 1457 &call->expected_version, NULL); 1458 if (ret < 0) 1459 return ret; 1460 xdr_decode_YFSVolSync(&bp, NULL); 1461 1462 _leave(" = 0 [done]"); 1463 return 0; 1464 } 1465 1466 /* 1467 * YFS.StoreStatus operation type 1468 */ 1469 static const struct afs_call_type yfs_RXYFSStoreStatus = { 1470 .name = "YFS.StoreStatus", 1471 .op = yfs_FS_StoreStatus, 1472 .deliver = yfs_deliver_fs_store_status, 1473 .destructor = afs_flat_call_destructor, 1474 }; 1475 1476 static const struct afs_call_type yfs_RXYFSStoreData64_as_Status = { 1477 .name = "YFS.StoreData64", 1478 .op = yfs_FS_StoreData64, 1479 .deliver = yfs_deliver_fs_store_status, 1480 .destructor = afs_flat_call_destructor, 1481 }; 1482 1483 /* 1484 * Set the attributes on a file, using YFS.StoreData64 rather than 1485 * YFS.StoreStatus so as to alter the file size also. 1486 */ 1487 static int yfs_fs_setattr_size(struct afs_fs_cursor *fc, struct iattr *attr) 1488 { 1489 struct afs_vnode *vnode = fc->vnode; 1490 struct afs_call *call; 1491 struct afs_net *net = afs_v2net(vnode); 1492 __be32 *bp; 1493 1494 _enter(",%x,{%llx:%llu},,", 1495 key_serial(fc->key), vnode->fid.vid, vnode->fid.vnode); 1496 1497 call = afs_alloc_flat_call(net, &yfs_RXYFSStoreData64_as_Status, 1498 sizeof(__be32) * 2 + 1499 sizeof(struct yfs_xdr_YFSFid) + 1500 sizeof(struct yfs_xdr_YFSStoreStatus) + 1501 sizeof(struct yfs_xdr_u64) * 3, 1502 sizeof(struct yfs_xdr_YFSFetchStatus) + 1503 sizeof(struct yfs_xdr_YFSVolSync)); 1504 if (!call) 1505 return -ENOMEM; 1506 1507 call->key = fc->key; 1508 call->reply[0] = vnode; 1509 call->expected_version = vnode->status.data_version + 1; 1510 1511 /* marshall the parameters */ 1512 bp = call->request; 1513 bp = xdr_encode_u32(bp, YFSSTOREDATA64); 1514 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1515 bp = xdr_encode_YFSFid(bp, &vnode->fid); 1516 bp = xdr_encode_YFS_StoreStatus(bp, attr); 1517 bp = xdr_encode_u64(bp, 0); /* position of start of write */ 1518 bp = xdr_encode_u64(bp, 0); /* size of write */ 1519 bp = xdr_encode_u64(bp, attr->ia_size); /* new file length */ 1520 yfs_check_req(call, bp); 1521 1522 afs_use_fs_server(call, fc->cbi); 1523 trace_afs_make_fs_call(call, &vnode->fid); 1524 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1525 } 1526 1527 /* 1528 * Set the attributes on a file, using YFS.StoreData64 if there's a change in 1529 * file size, and YFS.StoreStatus otherwise. 1530 */ 1531 int yfs_fs_setattr(struct afs_fs_cursor *fc, struct iattr *attr) 1532 { 1533 struct afs_vnode *vnode = fc->vnode; 1534 struct afs_call *call; 1535 struct afs_net *net = afs_v2net(vnode); 1536 __be32 *bp; 1537 1538 if (attr->ia_valid & ATTR_SIZE) 1539 return yfs_fs_setattr_size(fc, attr); 1540 1541 _enter(",%x,{%llx:%llu},,", 1542 key_serial(fc->key), vnode->fid.vid, vnode->fid.vnode); 1543 1544 call = afs_alloc_flat_call(net, &yfs_RXYFSStoreStatus, 1545 sizeof(__be32) * 2 + 1546 sizeof(struct yfs_xdr_YFSFid) + 1547 sizeof(struct yfs_xdr_YFSStoreStatus), 1548 sizeof(struct yfs_xdr_YFSFetchStatus) + 1549 sizeof(struct yfs_xdr_YFSVolSync)); 1550 if (!call) 1551 return -ENOMEM; 1552 1553 call->key = fc->key; 1554 call->reply[0] = vnode; 1555 call->expected_version = vnode->status.data_version; 1556 1557 /* marshall the parameters */ 1558 bp = call->request; 1559 bp = xdr_encode_u32(bp, YFSSTORESTATUS); 1560 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1561 bp = xdr_encode_YFSFid(bp, &vnode->fid); 1562 bp = xdr_encode_YFS_StoreStatus(bp, attr); 1563 yfs_check_req(call, bp); 1564 1565 afs_use_fs_server(call, fc->cbi); 1566 trace_afs_make_fs_call(call, &vnode->fid); 1567 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1568 } 1569 1570 /* 1571 * Deliver reply data to a YFS.GetVolumeStatus operation. 1572 */ 1573 static int yfs_deliver_fs_get_volume_status(struct afs_call *call) 1574 { 1575 const __be32 *bp; 1576 char *p; 1577 u32 size; 1578 int ret; 1579 1580 _enter("{%u}", call->unmarshall); 1581 1582 switch (call->unmarshall) { 1583 case 0: 1584 call->unmarshall++; 1585 afs_extract_to_buf(call, sizeof(struct yfs_xdr_YFSFetchVolumeStatus)); 1586 1587 /* extract the returned status record */ 1588 case 1: 1589 _debug("extract status"); 1590 ret = afs_extract_data(call, true); 1591 if (ret < 0) 1592 return ret; 1593 1594 bp = call->buffer; 1595 xdr_decode_YFSFetchVolumeStatus(&bp, call->reply[1]); 1596 call->unmarshall++; 1597 afs_extract_to_tmp(call); 1598 1599 /* extract the volume name length */ 1600 case 2: 1601 ret = afs_extract_data(call, true); 1602 if (ret < 0) 1603 return ret; 1604 1605 call->count = ntohl(call->tmp); 1606 _debug("volname length: %u", call->count); 1607 if (call->count >= AFSNAMEMAX) 1608 return afs_protocol_error(call, -EBADMSG, 1609 afs_eproto_volname_len); 1610 size = (call->count + 3) & ~3; /* It's padded */ 1611 afs_extract_begin(call, call->reply[2], size); 1612 call->unmarshall++; 1613 1614 /* extract the volume name */ 1615 case 3: 1616 _debug("extract volname"); 1617 ret = afs_extract_data(call, true); 1618 if (ret < 0) 1619 return ret; 1620 1621 p = call->reply[2]; 1622 p[call->count] = 0; 1623 _debug("volname '%s'", p); 1624 afs_extract_to_tmp(call); 1625 call->unmarshall++; 1626 1627 /* extract the offline message length */ 1628 case 4: 1629 ret = afs_extract_data(call, true); 1630 if (ret < 0) 1631 return ret; 1632 1633 call->count = ntohl(call->tmp); 1634 _debug("offline msg length: %u", call->count); 1635 if (call->count >= AFSNAMEMAX) 1636 return afs_protocol_error(call, -EBADMSG, 1637 afs_eproto_offline_msg_len); 1638 size = (call->count + 3) & ~3; /* It's padded */ 1639 afs_extract_begin(call, call->reply[2], size); 1640 call->unmarshall++; 1641 1642 /* extract the offline message */ 1643 case 5: 1644 _debug("extract offline"); 1645 ret = afs_extract_data(call, true); 1646 if (ret < 0) 1647 return ret; 1648 1649 p = call->reply[2]; 1650 p[call->count] = 0; 1651 _debug("offline '%s'", p); 1652 1653 afs_extract_to_tmp(call); 1654 call->unmarshall++; 1655 1656 /* extract the message of the day length */ 1657 case 6: 1658 ret = afs_extract_data(call, true); 1659 if (ret < 0) 1660 return ret; 1661 1662 call->count = ntohl(call->tmp); 1663 _debug("motd length: %u", call->count); 1664 if (call->count >= AFSNAMEMAX) 1665 return afs_protocol_error(call, -EBADMSG, 1666 afs_eproto_motd_len); 1667 size = (call->count + 3) & ~3; /* It's padded */ 1668 afs_extract_begin(call, call->reply[2], size); 1669 call->unmarshall++; 1670 1671 /* extract the message of the day */ 1672 case 7: 1673 _debug("extract motd"); 1674 ret = afs_extract_data(call, false); 1675 if (ret < 0) 1676 return ret; 1677 1678 p = call->reply[2]; 1679 p[call->count] = 0; 1680 _debug("motd '%s'", p); 1681 1682 call->unmarshall++; 1683 1684 case 8: 1685 break; 1686 } 1687 1688 _leave(" = 0 [done]"); 1689 return 0; 1690 } 1691 1692 /* 1693 * Destroy a YFS.GetVolumeStatus call. 1694 */ 1695 static void yfs_get_volume_status_call_destructor(struct afs_call *call) 1696 { 1697 kfree(call->reply[2]); 1698 call->reply[2] = NULL; 1699 afs_flat_call_destructor(call); 1700 } 1701 1702 /* 1703 * YFS.GetVolumeStatus operation type 1704 */ 1705 static const struct afs_call_type yfs_RXYFSGetVolumeStatus = { 1706 .name = "YFS.GetVolumeStatus", 1707 .op = yfs_FS_GetVolumeStatus, 1708 .deliver = yfs_deliver_fs_get_volume_status, 1709 .destructor = yfs_get_volume_status_call_destructor, 1710 }; 1711 1712 /* 1713 * fetch the status of a volume 1714 */ 1715 int yfs_fs_get_volume_status(struct afs_fs_cursor *fc, 1716 struct afs_volume_status *vs) 1717 { 1718 struct afs_vnode *vnode = fc->vnode; 1719 struct afs_call *call; 1720 struct afs_net *net = afs_v2net(vnode); 1721 __be32 *bp; 1722 void *tmpbuf; 1723 1724 _enter(""); 1725 1726 tmpbuf = kmalloc(AFSOPAQUEMAX, GFP_KERNEL); 1727 if (!tmpbuf) 1728 return -ENOMEM; 1729 1730 call = afs_alloc_flat_call(net, &yfs_RXYFSGetVolumeStatus, 1731 sizeof(__be32) * 2 + 1732 sizeof(struct yfs_xdr_u64), 1733 sizeof(struct yfs_xdr_YFSFetchVolumeStatus) + 1734 sizeof(__be32)); 1735 if (!call) { 1736 kfree(tmpbuf); 1737 return -ENOMEM; 1738 } 1739 1740 call->key = fc->key; 1741 call->reply[0] = vnode; 1742 call->reply[1] = vs; 1743 call->reply[2] = tmpbuf; 1744 1745 /* marshall the parameters */ 1746 bp = call->request; 1747 bp = xdr_encode_u32(bp, YFSGETVOLUMESTATUS); 1748 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1749 bp = xdr_encode_u64(bp, vnode->fid.vid); 1750 yfs_check_req(call, bp); 1751 1752 afs_use_fs_server(call, fc->cbi); 1753 trace_afs_make_fs_call(call, &vnode->fid); 1754 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1755 } 1756 1757 /* 1758 * Deliver reply data to an YFS.SetLock, YFS.ExtendLock or YFS.ReleaseLock 1759 */ 1760 static int yfs_deliver_fs_xxxx_lock(struct afs_call *call) 1761 { 1762 struct afs_vnode *vnode = call->reply[0]; 1763 const __be32 *bp; 1764 int ret; 1765 1766 _enter("{%u}", call->unmarshall); 1767 1768 ret = afs_transfer_reply(call); 1769 if (ret < 0) 1770 return ret; 1771 1772 /* unmarshall the reply once we've received all of it */ 1773 bp = call->buffer; 1774 ret = yfs_decode_status(call, &bp, &vnode->status, vnode, 1775 &call->expected_version, NULL); 1776 if (ret < 0) 1777 return ret; 1778 xdr_decode_YFSVolSync(&bp, NULL); 1779 1780 _leave(" = 0 [done]"); 1781 return 0; 1782 } 1783 1784 /* 1785 * YFS.SetLock operation type 1786 */ 1787 static const struct afs_call_type yfs_RXYFSSetLock = { 1788 .name = "YFS.SetLock", 1789 .op = yfs_FS_SetLock, 1790 .deliver = yfs_deliver_fs_xxxx_lock, 1791 .destructor = afs_flat_call_destructor, 1792 }; 1793 1794 /* 1795 * YFS.ExtendLock operation type 1796 */ 1797 static const struct afs_call_type yfs_RXYFSExtendLock = { 1798 .name = "YFS.ExtendLock", 1799 .op = yfs_FS_ExtendLock, 1800 .deliver = yfs_deliver_fs_xxxx_lock, 1801 .destructor = afs_flat_call_destructor, 1802 }; 1803 1804 /* 1805 * YFS.ReleaseLock operation type 1806 */ 1807 static const struct afs_call_type yfs_RXYFSReleaseLock = { 1808 .name = "YFS.ReleaseLock", 1809 .op = yfs_FS_ReleaseLock, 1810 .deliver = yfs_deliver_fs_xxxx_lock, 1811 .destructor = afs_flat_call_destructor, 1812 }; 1813 1814 /* 1815 * Set a lock on a file 1816 */ 1817 int yfs_fs_set_lock(struct afs_fs_cursor *fc, afs_lock_type_t type) 1818 { 1819 struct afs_vnode *vnode = fc->vnode; 1820 struct afs_call *call; 1821 struct afs_net *net = afs_v2net(vnode); 1822 __be32 *bp; 1823 1824 _enter(""); 1825 1826 call = afs_alloc_flat_call(net, &yfs_RXYFSSetLock, 1827 sizeof(__be32) * 2 + 1828 sizeof(struct yfs_xdr_YFSFid) + 1829 sizeof(__be32), 1830 sizeof(struct yfs_xdr_YFSFetchStatus) + 1831 sizeof(struct yfs_xdr_YFSVolSync)); 1832 if (!call) 1833 return -ENOMEM; 1834 1835 call->key = fc->key; 1836 call->reply[0] = vnode; 1837 1838 /* marshall the parameters */ 1839 bp = call->request; 1840 bp = xdr_encode_u32(bp, YFSSETLOCK); 1841 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1842 bp = xdr_encode_YFSFid(bp, &vnode->fid); 1843 bp = xdr_encode_u32(bp, type); 1844 yfs_check_req(call, bp); 1845 1846 afs_use_fs_server(call, fc->cbi); 1847 trace_afs_make_fs_call(call, &vnode->fid); 1848 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1849 } 1850 1851 /* 1852 * extend a lock on a file 1853 */ 1854 int yfs_fs_extend_lock(struct afs_fs_cursor *fc) 1855 { 1856 struct afs_vnode *vnode = fc->vnode; 1857 struct afs_call *call; 1858 struct afs_net *net = afs_v2net(vnode); 1859 __be32 *bp; 1860 1861 _enter(""); 1862 1863 call = afs_alloc_flat_call(net, &yfs_RXYFSExtendLock, 1864 sizeof(__be32) * 2 + 1865 sizeof(struct yfs_xdr_YFSFid), 1866 sizeof(struct yfs_xdr_YFSFetchStatus) + 1867 sizeof(struct yfs_xdr_YFSVolSync)); 1868 if (!call) 1869 return -ENOMEM; 1870 1871 call->key = fc->key; 1872 call->reply[0] = vnode; 1873 1874 /* marshall the parameters */ 1875 bp = call->request; 1876 bp = xdr_encode_u32(bp, YFSEXTENDLOCK); 1877 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1878 bp = xdr_encode_YFSFid(bp, &vnode->fid); 1879 yfs_check_req(call, bp); 1880 1881 afs_use_fs_server(call, fc->cbi); 1882 trace_afs_make_fs_call(call, &vnode->fid); 1883 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1884 } 1885 1886 /* 1887 * release a lock on a file 1888 */ 1889 int yfs_fs_release_lock(struct afs_fs_cursor *fc) 1890 { 1891 struct afs_vnode *vnode = fc->vnode; 1892 struct afs_call *call; 1893 struct afs_net *net = afs_v2net(vnode); 1894 __be32 *bp; 1895 1896 _enter(""); 1897 1898 call = afs_alloc_flat_call(net, &yfs_RXYFSReleaseLock, 1899 sizeof(__be32) * 2 + 1900 sizeof(struct yfs_xdr_YFSFid), 1901 sizeof(struct yfs_xdr_YFSFetchStatus) + 1902 sizeof(struct yfs_xdr_YFSVolSync)); 1903 if (!call) 1904 return -ENOMEM; 1905 1906 call->key = fc->key; 1907 call->reply[0] = vnode; 1908 1909 /* marshall the parameters */ 1910 bp = call->request; 1911 bp = xdr_encode_u32(bp, YFSRELEASELOCK); 1912 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 1913 bp = xdr_encode_YFSFid(bp, &vnode->fid); 1914 yfs_check_req(call, bp); 1915 1916 afs_use_fs_server(call, fc->cbi); 1917 trace_afs_make_fs_call(call, &vnode->fid); 1918 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 1919 } 1920 1921 /* 1922 * Deliver reply data to an FS.FetchStatus with no vnode. 1923 */ 1924 static int yfs_deliver_fs_fetch_status(struct afs_call *call) 1925 { 1926 struct afs_file_status *status = call->reply[1]; 1927 struct afs_callback *callback = call->reply[2]; 1928 struct afs_volsync *volsync = call->reply[3]; 1929 struct afs_vnode *vnode = call->reply[0]; 1930 const __be32 *bp; 1931 int ret; 1932 1933 ret = afs_transfer_reply(call); 1934 if (ret < 0) 1935 return ret; 1936 1937 _enter("{%llx:%llu}", vnode->fid.vid, vnode->fid.vnode); 1938 1939 /* unmarshall the reply once we've received all of it */ 1940 bp = call->buffer; 1941 ret = yfs_decode_status(call, &bp, status, vnode, 1942 &call->expected_version, NULL); 1943 if (ret < 0) 1944 return ret; 1945 xdr_decode_YFSCallBack_raw(&bp, callback); 1946 xdr_decode_YFSVolSync(&bp, volsync); 1947 1948 _leave(" = 0 [done]"); 1949 return 0; 1950 } 1951 1952 /* 1953 * YFS.FetchStatus operation type 1954 */ 1955 static const struct afs_call_type yfs_RXYFSFetchStatus = { 1956 .name = "YFS.FetchStatus", 1957 .op = yfs_FS_FetchStatus, 1958 .deliver = yfs_deliver_fs_fetch_status, 1959 .destructor = afs_flat_call_destructor, 1960 }; 1961 1962 /* 1963 * Fetch the status information for a fid without needing a vnode handle. 1964 */ 1965 int yfs_fs_fetch_status(struct afs_fs_cursor *fc, 1966 struct afs_net *net, 1967 struct afs_fid *fid, 1968 struct afs_file_status *status, 1969 struct afs_callback *callback, 1970 struct afs_volsync *volsync) 1971 { 1972 struct afs_call *call; 1973 __be32 *bp; 1974 1975 _enter(",%x,{%llx:%llu},,", 1976 key_serial(fc->key), fid->vid, fid->vnode); 1977 1978 call = afs_alloc_flat_call(net, &yfs_RXYFSFetchStatus, 1979 sizeof(__be32) * 2 + 1980 sizeof(struct yfs_xdr_YFSFid), 1981 sizeof(struct yfs_xdr_YFSFetchStatus) + 1982 sizeof(struct yfs_xdr_YFSCallBack) + 1983 sizeof(struct yfs_xdr_YFSVolSync)); 1984 if (!call) { 1985 fc->ac.error = -ENOMEM; 1986 return -ENOMEM; 1987 } 1988 1989 call->key = fc->key; 1990 call->reply[0] = NULL; /* vnode for fid[0] */ 1991 call->reply[1] = status; 1992 call->reply[2] = callback; 1993 call->reply[3] = volsync; 1994 call->expected_version = 1; /* vnode->status.data_version */ 1995 1996 /* marshall the parameters */ 1997 bp = call->request; 1998 bp = xdr_encode_u32(bp, YFSFETCHSTATUS); 1999 bp = xdr_encode_u32(bp, 0); /* RPC flags */ 2000 bp = xdr_encode_YFSFid(bp, fid); 2001 yfs_check_req(call, bp); 2002 2003 call->cb_break = fc->cb_break; 2004 afs_use_fs_server(call, fc->cbi); 2005 trace_afs_make_fs_call(call, fid); 2006 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 2007 } 2008 2009 /* 2010 * Deliver reply data to an YFS.InlineBulkStatus call 2011 */ 2012 static int yfs_deliver_fs_inline_bulk_status(struct afs_call *call) 2013 { 2014 struct afs_file_status *statuses; 2015 struct afs_callback *callbacks; 2016 struct afs_vnode *vnode = call->reply[0]; 2017 const __be32 *bp; 2018 u32 tmp; 2019 int ret; 2020 2021 _enter("{%u}", call->unmarshall); 2022 2023 switch (call->unmarshall) { 2024 case 0: 2025 afs_extract_to_tmp(call); 2026 call->unmarshall++; 2027 2028 /* Extract the file status count and array in two steps */ 2029 case 1: 2030 _debug("extract status count"); 2031 ret = afs_extract_data(call, true); 2032 if (ret < 0) 2033 return ret; 2034 2035 tmp = ntohl(call->tmp); 2036 _debug("status count: %u/%u", tmp, call->count2); 2037 if (tmp != call->count2) 2038 return afs_protocol_error(call, -EBADMSG, 2039 afs_eproto_ibulkst_count); 2040 2041 call->count = 0; 2042 call->unmarshall++; 2043 more_counts: 2044 afs_extract_to_buf(call, sizeof(struct yfs_xdr_YFSFetchStatus)); 2045 2046 case 2: 2047 _debug("extract status array %u", call->count); 2048 ret = afs_extract_data(call, true); 2049 if (ret < 0) 2050 return ret; 2051 2052 bp = call->buffer; 2053 statuses = call->reply[1]; 2054 ret = yfs_decode_status(call, &bp, &statuses[call->count], 2055 call->count == 0 ? vnode : NULL, 2056 NULL, NULL); 2057 if (ret < 0) 2058 return ret; 2059 2060 call->count++; 2061 if (call->count < call->count2) 2062 goto more_counts; 2063 2064 call->count = 0; 2065 call->unmarshall++; 2066 afs_extract_to_tmp(call); 2067 2068 /* Extract the callback count and array in two steps */ 2069 case 3: 2070 _debug("extract CB count"); 2071 ret = afs_extract_data(call, true); 2072 if (ret < 0) 2073 return ret; 2074 2075 tmp = ntohl(call->tmp); 2076 _debug("CB count: %u", tmp); 2077 if (tmp != call->count2) 2078 return afs_protocol_error(call, -EBADMSG, 2079 afs_eproto_ibulkst_cb_count); 2080 call->count = 0; 2081 call->unmarshall++; 2082 more_cbs: 2083 afs_extract_to_buf(call, sizeof(struct yfs_xdr_YFSCallBack)); 2084 2085 case 4: 2086 _debug("extract CB array"); 2087 ret = afs_extract_data(call, true); 2088 if (ret < 0) 2089 return ret; 2090 2091 _debug("unmarshall CB array"); 2092 bp = call->buffer; 2093 callbacks = call->reply[2]; 2094 xdr_decode_YFSCallBack_raw(&bp, &callbacks[call->count]); 2095 statuses = call->reply[1]; 2096 if (call->count == 0 && vnode && statuses[0].abort_code == 0) { 2097 bp = call->buffer; 2098 xdr_decode_YFSCallBack(call, vnode, &bp); 2099 } 2100 call->count++; 2101 if (call->count < call->count2) 2102 goto more_cbs; 2103 2104 afs_extract_to_buf(call, sizeof(struct yfs_xdr_YFSVolSync)); 2105 call->unmarshall++; 2106 2107 case 5: 2108 ret = afs_extract_data(call, false); 2109 if (ret < 0) 2110 return ret; 2111 2112 bp = call->buffer; 2113 xdr_decode_YFSVolSync(&bp, call->reply[3]); 2114 2115 call->unmarshall++; 2116 2117 case 6: 2118 break; 2119 } 2120 2121 _leave(" = 0 [done]"); 2122 return 0; 2123 } 2124 2125 /* 2126 * FS.InlineBulkStatus operation type 2127 */ 2128 static const struct afs_call_type yfs_RXYFSInlineBulkStatus = { 2129 .name = "YFS.InlineBulkStatus", 2130 .op = yfs_FS_InlineBulkStatus, 2131 .deliver = yfs_deliver_fs_inline_bulk_status, 2132 .destructor = afs_flat_call_destructor, 2133 }; 2134 2135 /* 2136 * Fetch the status information for up to 1024 files 2137 */ 2138 int yfs_fs_inline_bulk_status(struct afs_fs_cursor *fc, 2139 struct afs_net *net, 2140 struct afs_fid *fids, 2141 struct afs_file_status *statuses, 2142 struct afs_callback *callbacks, 2143 unsigned int nr_fids, 2144 struct afs_volsync *volsync) 2145 { 2146 struct afs_call *call; 2147 __be32 *bp; 2148 int i; 2149 2150 _enter(",%x,{%llx:%llu},%u", 2151 key_serial(fc->key), fids[0].vid, fids[1].vnode, nr_fids); 2152 2153 call = afs_alloc_flat_call(net, &yfs_RXYFSInlineBulkStatus, 2154 sizeof(__be32) + 2155 sizeof(__be32) + 2156 sizeof(__be32) + 2157 sizeof(struct yfs_xdr_YFSFid) * nr_fids, 2158 sizeof(struct yfs_xdr_YFSFetchStatus)); 2159 if (!call) { 2160 fc->ac.error = -ENOMEM; 2161 return -ENOMEM; 2162 } 2163 2164 call->key = fc->key; 2165 call->reply[0] = NULL; /* vnode for fid[0] */ 2166 call->reply[1] = statuses; 2167 call->reply[2] = callbacks; 2168 call->reply[3] = volsync; 2169 call->count2 = nr_fids; 2170 2171 /* marshall the parameters */ 2172 bp = call->request; 2173 bp = xdr_encode_u32(bp, YFSINLINEBULKSTATUS); 2174 bp = xdr_encode_u32(bp, 0); /* RPCFlags */ 2175 bp = xdr_encode_u32(bp, nr_fids); 2176 for (i = 0; i < nr_fids; i++) 2177 bp = xdr_encode_YFSFid(bp, &fids[i]); 2178 yfs_check_req(call, bp); 2179 2180 call->cb_break = fc->cb_break; 2181 afs_use_fs_server(call, fc->cbi); 2182 trace_afs_make_fs_call(call, &fids[0]); 2183 return afs_make_call(&fc->ac, call, GFP_NOFS, false); 2184 } 2185