linux/fs/afs/cmservice.c
<<
>>
Prefs
   1// SPDX-License-Identifier: GPL-2.0-or-later
   2/* AFS Cache Manager Service
   3 *
   4 * Copyright (C) 2002 Red Hat, Inc. All Rights Reserved.
   5 * Written by David Howells (dhowells@redhat.com)
   6 */
   7
   8#include <linux/module.h>
   9#include <linux/init.h>
  10#include <linux/slab.h>
  11#include <linux/sched.h>
  12#include <linux/ip.h>
  13#include "internal.h"
  14#include "afs_cm.h"
  15#include "protocol_yfs.h"
  16
  17static int afs_deliver_cb_init_call_back_state(struct afs_call *);
  18static int afs_deliver_cb_init_call_back_state3(struct afs_call *);
  19static int afs_deliver_cb_probe(struct afs_call *);
  20static int afs_deliver_cb_callback(struct afs_call *);
  21static int afs_deliver_cb_probe_uuid(struct afs_call *);
  22static int afs_deliver_cb_tell_me_about_yourself(struct afs_call *);
  23static void afs_cm_destructor(struct afs_call *);
  24static void SRXAFSCB_CallBack(struct work_struct *);
  25static void SRXAFSCB_InitCallBackState(struct work_struct *);
  26static void SRXAFSCB_Probe(struct work_struct *);
  27static void SRXAFSCB_ProbeUuid(struct work_struct *);
  28static void SRXAFSCB_TellMeAboutYourself(struct work_struct *);
  29
  30static int afs_deliver_yfs_cb_callback(struct afs_call *);
  31
  32#define CM_NAME(name) \
  33        char afs_SRXCB##name##_name[] __tracepoint_string =     \
  34                "CB." #name
  35
  36/*
  37 * CB.CallBack operation type
  38 */
  39static CM_NAME(CallBack);
  40static const struct afs_call_type afs_SRXCBCallBack = {
  41        .name           = afs_SRXCBCallBack_name,
  42        .deliver        = afs_deliver_cb_callback,
  43        .destructor     = afs_cm_destructor,
  44        .work           = SRXAFSCB_CallBack,
  45};
  46
  47/*
  48 * CB.InitCallBackState operation type
  49 */
  50static CM_NAME(InitCallBackState);
  51static const struct afs_call_type afs_SRXCBInitCallBackState = {
  52        .name           = afs_SRXCBInitCallBackState_name,
  53        .deliver        = afs_deliver_cb_init_call_back_state,
  54        .destructor     = afs_cm_destructor,
  55        .work           = SRXAFSCB_InitCallBackState,
  56};
  57
  58/*
  59 * CB.InitCallBackState3 operation type
  60 */
  61static CM_NAME(InitCallBackState3);
  62static const struct afs_call_type afs_SRXCBInitCallBackState3 = {
  63        .name           = afs_SRXCBInitCallBackState3_name,
  64        .deliver        = afs_deliver_cb_init_call_back_state3,
  65        .destructor     = afs_cm_destructor,
  66        .work           = SRXAFSCB_InitCallBackState,
  67};
  68
  69/*
  70 * CB.Probe operation type
  71 */
  72static CM_NAME(Probe);
  73static const struct afs_call_type afs_SRXCBProbe = {
  74        .name           = afs_SRXCBProbe_name,
  75        .deliver        = afs_deliver_cb_probe,
  76        .destructor     = afs_cm_destructor,
  77        .work           = SRXAFSCB_Probe,
  78};
  79
  80/*
  81 * CB.ProbeUuid operation type
  82 */
  83static CM_NAME(ProbeUuid);
  84static const struct afs_call_type afs_SRXCBProbeUuid = {
  85        .name           = afs_SRXCBProbeUuid_name,
  86        .deliver        = afs_deliver_cb_probe_uuid,
  87        .destructor     = afs_cm_destructor,
  88        .work           = SRXAFSCB_ProbeUuid,
  89};
  90
  91/*
  92 * CB.TellMeAboutYourself operation type
  93 */
  94static CM_NAME(TellMeAboutYourself);
  95static const struct afs_call_type afs_SRXCBTellMeAboutYourself = {
  96        .name           = afs_SRXCBTellMeAboutYourself_name,
  97        .deliver        = afs_deliver_cb_tell_me_about_yourself,
  98        .destructor     = afs_cm_destructor,
  99        .work           = SRXAFSCB_TellMeAboutYourself,
 100};
 101
 102/*
 103 * YFS CB.CallBack operation type
 104 */
 105static CM_NAME(YFS_CallBack);
 106static const struct afs_call_type afs_SRXYFSCB_CallBack = {
 107        .name           = afs_SRXCBYFS_CallBack_name,
 108        .deliver        = afs_deliver_yfs_cb_callback,
 109        .destructor     = afs_cm_destructor,
 110        .work           = SRXAFSCB_CallBack,
 111};
 112
 113/*
 114 * route an incoming cache manager call
 115 * - return T if supported, F if not
 116 */
 117bool afs_cm_incoming_call(struct afs_call *call)
 118{
 119        _enter("{%u, CB.OP %u}", call->service_id, call->operation_ID);
 120
 121        call->epoch = rxrpc_kernel_get_epoch(call->net->socket, call->rxcall);
 122
 123        switch (call->operation_ID) {
 124        case CBCallBack:
 125                call->type = &afs_SRXCBCallBack;
 126                return true;
 127        case CBInitCallBackState:
 128                call->type = &afs_SRXCBInitCallBackState;
 129                return true;
 130        case CBInitCallBackState3:
 131                call->type = &afs_SRXCBInitCallBackState3;
 132                return true;
 133        case CBProbe:
 134                call->type = &afs_SRXCBProbe;
 135                return true;
 136        case CBProbeUuid:
 137                call->type = &afs_SRXCBProbeUuid;
 138                return true;
 139        case CBTellMeAboutYourself:
 140                call->type = &afs_SRXCBTellMeAboutYourself;
 141                return true;
 142        case YFSCBCallBack:
 143                if (call->service_id != YFS_CM_SERVICE)
 144                        return false;
 145                call->type = &afs_SRXYFSCB_CallBack;
 146                return true;
 147        default:
 148                return false;
 149        }
 150}
 151
 152/*
 153 * Record a probe to the cache manager from a server.
 154 */
 155static int afs_record_cm_probe(struct afs_call *call, struct afs_server *server)
 156{
 157        _enter("");
 158
 159        if (test_bit(AFS_SERVER_FL_HAVE_EPOCH, &server->flags) &&
 160            !test_bit(AFS_SERVER_FL_PROBING, &server->flags)) {
 161                if (server->cm_epoch == call->epoch)
 162                        return 0;
 163
 164                if (!server->probe.said_rebooted) {
 165                        pr_notice("kAFS: FS rebooted %pU\n", &server->uuid);
 166                        server->probe.said_rebooted = true;
 167                }
 168        }
 169
 170        spin_lock(&server->probe_lock);
 171
 172        if (!test_bit(AFS_SERVER_FL_HAVE_EPOCH, &server->flags)) {
 173                server->cm_epoch = call->epoch;
 174                server->probe.cm_epoch = call->epoch;
 175                goto out;
 176        }
 177
 178        if (server->probe.cm_probed &&
 179            call->epoch != server->probe.cm_epoch &&
 180            !server->probe.said_inconsistent) {
 181                pr_notice("kAFS: FS endpoints inconsistent %pU\n",
 182                          &server->uuid);
 183                server->probe.said_inconsistent = true;
 184        }
 185
 186        if (!server->probe.cm_probed || call->epoch == server->cm_epoch)
 187                server->probe.cm_epoch = server->cm_epoch;
 188
 189out:
 190        server->probe.cm_probed = true;
 191        spin_unlock(&server->probe_lock);
 192        return 0;
 193}
 194
 195/*
 196 * Find the server record by peer address and record a probe to the cache
 197 * manager from a server.
 198 */
 199static int afs_find_cm_server_by_peer(struct afs_call *call)
 200{
 201        struct sockaddr_rxrpc srx;
 202        struct afs_server *server;
 203
 204        rxrpc_kernel_get_peer(call->net->socket, call->rxcall, &srx);
 205
 206        server = afs_find_server(call->net, &srx);
 207        if (!server) {
 208                trace_afs_cm_no_server(call, &srx);
 209                return 0;
 210        }
 211
 212        call->server = server;
 213        return afs_record_cm_probe(call, server);
 214}
 215
 216/*
 217 * Find the server record by server UUID and record a probe to the cache
 218 * manager from a server.
 219 */
 220static int afs_find_cm_server_by_uuid(struct afs_call *call,
 221                                      struct afs_uuid *uuid)
 222{
 223        struct afs_server *server;
 224
 225        rcu_read_lock();
 226        server = afs_find_server_by_uuid(call->net, call->request);
 227        rcu_read_unlock();
 228        if (!server) {
 229                trace_afs_cm_no_server_u(call, call->request);
 230                return 0;
 231        }
 232
 233        call->server = server;
 234        return afs_record_cm_probe(call, server);
 235}
 236
 237/*
 238 * Clean up a cache manager call.
 239 */
 240static void afs_cm_destructor(struct afs_call *call)
 241{
 242        kfree(call->buffer);
 243        call->buffer = NULL;
 244}
 245
 246/*
 247 * The server supplied a list of callbacks that it wanted to break.
 248 */
 249static void SRXAFSCB_CallBack(struct work_struct *work)
 250{
 251        struct afs_call *call = container_of(work, struct afs_call, work);
 252
 253        _enter("");
 254
 255        /* We need to break the callbacks before sending the reply as the
 256         * server holds up change visibility till it receives our reply so as
 257         * to maintain cache coherency.
 258         */
 259        if (call->server)
 260                afs_break_callbacks(call->server, call->count, call->request);
 261
 262        afs_send_empty_reply(call);
 263        afs_put_call(call);
 264        _leave("");
 265}
 266
 267/*
 268 * deliver request data to a CB.CallBack call
 269 */
 270static int afs_deliver_cb_callback(struct afs_call *call)
 271{
 272        struct afs_callback_break *cb;
 273        __be32 *bp;
 274        int ret, loop;
 275
 276        _enter("{%u}", call->unmarshall);
 277
 278        switch (call->unmarshall) {
 279        case 0:
 280                afs_extract_to_tmp(call);
 281                call->unmarshall++;
 282
 283                /* extract the FID array and its count in two steps */
 284                /* fall through */
 285        case 1:
 286                _debug("extract FID count");
 287                ret = afs_extract_data(call, true);
 288                if (ret < 0)
 289                        return ret;
 290
 291                call->count = ntohl(call->tmp);
 292                _debug("FID count: %u", call->count);
 293                if (call->count > AFSCBMAX)
 294                        return afs_protocol_error(call, -EBADMSG,
 295                                                  afs_eproto_cb_fid_count);
 296
 297                call->buffer = kmalloc(array3_size(call->count, 3, 4),
 298                                       GFP_KERNEL);
 299                if (!call->buffer)
 300                        return -ENOMEM;
 301                afs_extract_to_buf(call, call->count * 3 * 4);
 302                call->unmarshall++;
 303
 304                /* Fall through */
 305        case 2:
 306                _debug("extract FID array");
 307                ret = afs_extract_data(call, true);
 308                if (ret < 0)
 309                        return ret;
 310
 311                _debug("unmarshall FID array");
 312                call->request = kcalloc(call->count,
 313                                        sizeof(struct afs_callback_break),
 314                                        GFP_KERNEL);
 315                if (!call->request)
 316                        return -ENOMEM;
 317
 318                cb = call->request;
 319                bp = call->buffer;
 320                for (loop = call->count; loop > 0; loop--, cb++) {
 321                        cb->fid.vid     = ntohl(*bp++);
 322                        cb->fid.vnode   = ntohl(*bp++);
 323                        cb->fid.unique  = ntohl(*bp++);
 324                }
 325
 326                afs_extract_to_tmp(call);
 327                call->unmarshall++;
 328
 329                /* extract the callback array and its count in two steps */
 330                /* fall through */
 331        case 3:
 332                _debug("extract CB count");
 333                ret = afs_extract_data(call, true);
 334                if (ret < 0)
 335                        return ret;
 336
 337                call->count2 = ntohl(call->tmp);
 338                _debug("CB count: %u", call->count2);
 339                if (call->count2 != call->count && call->count2 != 0)
 340                        return afs_protocol_error(call, -EBADMSG,
 341                                                  afs_eproto_cb_count);
 342                call->_iter = &call->iter;
 343                iov_iter_discard(&call->iter, READ, call->count2 * 3 * 4);
 344                call->unmarshall++;
 345
 346                /* Fall through */
 347        case 4:
 348                _debug("extract discard %zu/%u",
 349                       iov_iter_count(&call->iter), call->count2 * 3 * 4);
 350
 351                ret = afs_extract_data(call, false);
 352                if (ret < 0)
 353                        return ret;
 354
 355                call->unmarshall++;
 356        case 5:
 357                break;
 358        }
 359
 360        if (!afs_check_call_state(call, AFS_CALL_SV_REPLYING))
 361                return afs_io_error(call, afs_io_error_cm_reply);
 362
 363        /* we'll need the file server record as that tells us which set of
 364         * vnodes to operate upon */
 365        return afs_find_cm_server_by_peer(call);
 366}
 367
 368/*
 369 * allow the fileserver to request callback state (re-)initialisation
 370 */
 371static void SRXAFSCB_InitCallBackState(struct work_struct *work)
 372{
 373        struct afs_call *call = container_of(work, struct afs_call, work);
 374
 375        _enter("{%p}", call->server);
 376
 377        if (call->server)
 378                afs_init_callback_state(call->server);
 379        afs_send_empty_reply(call);
 380        afs_put_call(call);
 381        _leave("");
 382}
 383
 384/*
 385 * deliver request data to a CB.InitCallBackState call
 386 */
 387static int afs_deliver_cb_init_call_back_state(struct afs_call *call)
 388{
 389        int ret;
 390
 391        _enter("");
 392
 393        afs_extract_discard(call, 0);
 394        ret = afs_extract_data(call, false);
 395        if (ret < 0)
 396                return ret;
 397
 398        /* we'll need the file server record as that tells us which set of
 399         * vnodes to operate upon */
 400        return afs_find_cm_server_by_peer(call);
 401}
 402
 403/*
 404 * deliver request data to a CB.InitCallBackState3 call
 405 */
 406static int afs_deliver_cb_init_call_back_state3(struct afs_call *call)
 407{
 408        struct afs_uuid *r;
 409        unsigned loop;
 410        __be32 *b;
 411        int ret;
 412
 413        _enter("");
 414
 415        _enter("{%u}", call->unmarshall);
 416
 417        switch (call->unmarshall) {
 418        case 0:
 419                call->buffer = kmalloc_array(11, sizeof(__be32), GFP_KERNEL);
 420                if (!call->buffer)
 421                        return -ENOMEM;
 422                afs_extract_to_buf(call, 11 * sizeof(__be32));
 423                call->unmarshall++;
 424
 425                /* Fall through */
 426        case 1:
 427                _debug("extract UUID");
 428                ret = afs_extract_data(call, false);
 429                switch (ret) {
 430                case 0:         break;
 431                case -EAGAIN:   return 0;
 432                default:        return ret;
 433                }
 434
 435                _debug("unmarshall UUID");
 436                call->request = kmalloc(sizeof(struct afs_uuid), GFP_KERNEL);
 437                if (!call->request)
 438                        return -ENOMEM;
 439
 440                b = call->buffer;
 441                r = call->request;
 442                r->time_low                     = b[0];
 443                r->time_mid                     = htons(ntohl(b[1]));
 444                r->time_hi_and_version          = htons(ntohl(b[2]));
 445                r->clock_seq_hi_and_reserved    = ntohl(b[3]);
 446                r->clock_seq_low                = ntohl(b[4]);
 447
 448                for (loop = 0; loop < 6; loop++)
 449                        r->node[loop] = ntohl(b[loop + 5]);
 450
 451                call->unmarshall++;
 452
 453        case 2:
 454                break;
 455        }
 456
 457        if (!afs_check_call_state(call, AFS_CALL_SV_REPLYING))
 458                return afs_io_error(call, afs_io_error_cm_reply);
 459
 460        /* we'll need the file server record as that tells us which set of
 461         * vnodes to operate upon */
 462        return afs_find_cm_server_by_uuid(call, call->request);
 463}
 464
 465/*
 466 * allow the fileserver to see if the cache manager is still alive
 467 */
 468static void SRXAFSCB_Probe(struct work_struct *work)
 469{
 470        struct afs_call *call = container_of(work, struct afs_call, work);
 471
 472        _enter("");
 473        afs_send_empty_reply(call);
 474        afs_put_call(call);
 475        _leave("");
 476}
 477
 478/*
 479 * deliver request data to a CB.Probe call
 480 */
 481static int afs_deliver_cb_probe(struct afs_call *call)
 482{
 483        int ret;
 484
 485        _enter("");
 486
 487        afs_extract_discard(call, 0);
 488        ret = afs_extract_data(call, false);
 489        if (ret < 0)
 490                return ret;
 491
 492        if (!afs_check_call_state(call, AFS_CALL_SV_REPLYING))
 493                return afs_io_error(call, afs_io_error_cm_reply);
 494        return afs_find_cm_server_by_peer(call);
 495}
 496
 497/*
 498 * allow the fileserver to quickly find out if the fileserver has been rebooted
 499 */
 500static void SRXAFSCB_ProbeUuid(struct work_struct *work)
 501{
 502        struct afs_call *call = container_of(work, struct afs_call, work);
 503        struct afs_uuid *r = call->request;
 504
 505        struct {
 506                __be32  match;
 507        } reply;
 508
 509        _enter("");
 510
 511        if (memcmp(r, &call->net->uuid, sizeof(call->net->uuid)) == 0)
 512                reply.match = htonl(0);
 513        else
 514                reply.match = htonl(1);
 515
 516        afs_send_simple_reply(call, &reply, sizeof(reply));
 517        afs_put_call(call);
 518        _leave("");
 519}
 520
 521/*
 522 * deliver request data to a CB.ProbeUuid call
 523 */
 524static int afs_deliver_cb_probe_uuid(struct afs_call *call)
 525{
 526        struct afs_uuid *r;
 527        unsigned loop;
 528        __be32 *b;
 529        int ret;
 530
 531        _enter("{%u}", call->unmarshall);
 532
 533        switch (call->unmarshall) {
 534        case 0:
 535                call->buffer = kmalloc_array(11, sizeof(__be32), GFP_KERNEL);
 536                if (!call->buffer)
 537                        return -ENOMEM;
 538                afs_extract_to_buf(call, 11 * sizeof(__be32));
 539                call->unmarshall++;
 540
 541                /* Fall through */
 542        case 1:
 543                _debug("extract UUID");
 544                ret = afs_extract_data(call, false);
 545                switch (ret) {
 546                case 0:         break;
 547                case -EAGAIN:   return 0;
 548                default:        return ret;
 549                }
 550
 551                _debug("unmarshall UUID");
 552                call->request = kmalloc(sizeof(struct afs_uuid), GFP_KERNEL);
 553                if (!call->request)
 554                        return -ENOMEM;
 555
 556                b = call->buffer;
 557                r = call->request;
 558                r->time_low                     = b[0];
 559                r->time_mid                     = htons(ntohl(b[1]));
 560                r->time_hi_and_version          = htons(ntohl(b[2]));
 561                r->clock_seq_hi_and_reserved    = ntohl(b[3]);
 562                r->clock_seq_low                = ntohl(b[4]);
 563
 564                for (loop = 0; loop < 6; loop++)
 565                        r->node[loop] = ntohl(b[loop + 5]);
 566
 567                call->unmarshall++;
 568
 569        case 2:
 570                break;
 571        }
 572
 573        if (!afs_check_call_state(call, AFS_CALL_SV_REPLYING))
 574                return afs_io_error(call, afs_io_error_cm_reply);
 575        return afs_find_cm_server_by_uuid(call, call->request);
 576}
 577
 578/*
 579 * allow the fileserver to ask about the cache manager's capabilities
 580 */
 581static void SRXAFSCB_TellMeAboutYourself(struct work_struct *work)
 582{
 583        struct afs_interface *ifs;
 584        struct afs_call *call = container_of(work, struct afs_call, work);
 585        int loop, nifs;
 586
 587        struct {
 588                struct /* InterfaceAddr */ {
 589                        __be32 nifs;
 590                        __be32 uuid[11];
 591                        __be32 ifaddr[32];
 592                        __be32 netmask[32];
 593                        __be32 mtu[32];
 594                } ia;
 595                struct /* Capabilities */ {
 596                        __be32 capcount;
 597                        __be32 caps[1];
 598                } cap;
 599        } reply;
 600
 601        _enter("");
 602
 603        nifs = 0;
 604        ifs = kcalloc(32, sizeof(*ifs), GFP_KERNEL);
 605        if (ifs) {
 606                nifs = afs_get_ipv4_interfaces(call->net, ifs, 32, false);
 607                if (nifs < 0) {
 608                        kfree(ifs);
 609                        ifs = NULL;
 610                        nifs = 0;
 611                }
 612        }
 613
 614        memset(&reply, 0, sizeof(reply));
 615        reply.ia.nifs = htonl(nifs);
 616
 617        reply.ia.uuid[0] = call->net->uuid.time_low;
 618        reply.ia.uuid[1] = htonl(ntohs(call->net->uuid.time_mid));
 619        reply.ia.uuid[2] = htonl(ntohs(call->net->uuid.time_hi_and_version));
 620        reply.ia.uuid[3] = htonl((s8) call->net->uuid.clock_seq_hi_and_reserved);
 621        reply.ia.uuid[4] = htonl((s8) call->net->uuid.clock_seq_low);
 622        for (loop = 0; loop < 6; loop++)
 623                reply.ia.uuid[loop + 5] = htonl((s8) call->net->uuid.node[loop]);
 624
 625        if (ifs) {
 626                for (loop = 0; loop < nifs; loop++) {
 627                        reply.ia.ifaddr[loop] = ifs[loop].address.s_addr;
 628                        reply.ia.netmask[loop] = ifs[loop].netmask.s_addr;
 629                        reply.ia.mtu[loop] = htonl(ifs[loop].mtu);
 630                }
 631                kfree(ifs);
 632        }
 633
 634        reply.cap.capcount = htonl(1);
 635        reply.cap.caps[0] = htonl(AFS_CAP_ERROR_TRANSLATION);
 636        afs_send_simple_reply(call, &reply, sizeof(reply));
 637        afs_put_call(call);
 638        _leave("");
 639}
 640
 641/*
 642 * deliver request data to a CB.TellMeAboutYourself call
 643 */
 644static int afs_deliver_cb_tell_me_about_yourself(struct afs_call *call)
 645{
 646        int ret;
 647
 648        _enter("");
 649
 650        afs_extract_discard(call, 0);
 651        ret = afs_extract_data(call, false);
 652        if (ret < 0)
 653                return ret;
 654
 655        if (!afs_check_call_state(call, AFS_CALL_SV_REPLYING))
 656                return afs_io_error(call, afs_io_error_cm_reply);
 657        return afs_find_cm_server_by_peer(call);
 658}
 659
 660/*
 661 * deliver request data to a YFS CB.CallBack call
 662 */
 663static int afs_deliver_yfs_cb_callback(struct afs_call *call)
 664{
 665        struct afs_callback_break *cb;
 666        struct yfs_xdr_YFSFid *bp;
 667        size_t size;
 668        int ret, loop;
 669
 670        _enter("{%u}", call->unmarshall);
 671
 672        switch (call->unmarshall) {
 673        case 0:
 674                afs_extract_to_tmp(call);
 675                call->unmarshall++;
 676
 677                /* extract the FID array and its count in two steps */
 678                /* Fall through */
 679        case 1:
 680                _debug("extract FID count");
 681                ret = afs_extract_data(call, true);
 682                if (ret < 0)
 683                        return ret;
 684
 685                call->count = ntohl(call->tmp);
 686                _debug("FID count: %u", call->count);
 687                if (call->count > YFSCBMAX)
 688                        return afs_protocol_error(call, -EBADMSG,
 689                                                  afs_eproto_cb_fid_count);
 690
 691                size = array_size(call->count, sizeof(struct yfs_xdr_YFSFid));
 692                call->buffer = kmalloc(size, GFP_KERNEL);
 693                if (!call->buffer)
 694                        return -ENOMEM;
 695                afs_extract_to_buf(call, size);
 696                call->unmarshall++;
 697
 698                /* Fall through */
 699        case 2:
 700                _debug("extract FID array");
 701                ret = afs_extract_data(call, false);
 702                if (ret < 0)
 703                        return ret;
 704
 705                _debug("unmarshall FID array");
 706                call->request = kcalloc(call->count,
 707                                        sizeof(struct afs_callback_break),
 708                                        GFP_KERNEL);
 709                if (!call->request)
 710                        return -ENOMEM;
 711
 712                cb = call->request;
 713                bp = call->buffer;
 714                for (loop = call->count; loop > 0; loop--, cb++) {
 715                        cb->fid.vid     = xdr_to_u64(bp->volume);
 716                        cb->fid.vnode   = xdr_to_u64(bp->vnode.lo);
 717                        cb->fid.vnode_hi = ntohl(bp->vnode.hi);
 718                        cb->fid.unique  = ntohl(bp->vnode.unique);
 719                        bp++;
 720                }
 721
 722                afs_extract_to_tmp(call);
 723                call->unmarshall++;
 724
 725        case 3:
 726                break;
 727        }
 728
 729        if (!afs_check_call_state(call, AFS_CALL_SV_REPLYING))
 730                return afs_io_error(call, afs_io_error_cm_reply);
 731
 732        /* We'll need the file server record as that tells us which set of
 733         * vnodes to operate upon.
 734         */
 735        return afs_find_cm_server_by_peer(call);
 736}
 737