d87aa3edfc4a1b3c86f52d5ff04ae61fc9984874
[openafs.git] / src / WINNT / afsd / cm_getaddrs.c
1 /*
2  * Copyright (c) 2014 Your File System, Inc.
3  * All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions are met:
7  *
8  * - Redistributions of source code must retain the above copyright notice,
9  *   this list of conditions and the following disclaimer.
10  * - Redistributions in binary form must reproduce the above copyright notice,
11  *   this list of conditions and the following disclaimer in the documentation
12  *   and/or other materials provided with the distribution.
13  * - Neither the name of Secure Endpoints Inc. nor the names of its contributors
14  *   may be used to endorse or promote products derived from this software without
15  *   specific prior written permission from Secure Endpoints, Inc. and
16  *   Your File System, Inc.
17  *
18  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
19  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
20  * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
21  * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
22  * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
23  * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
24  * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
25  * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
26  * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
27  * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
28  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29  */
30
31 #include <afsconfig.h>
32 #include <afs/param.h>
33 #include <roken.h>
34
35 #include <afs/stds.h>
36 #include "afsd.h"
37 #include "cm_getaddrs.h"
38
39 /*
40  * cm_GetAddrsU takes as input a uuid and a unique value which
41  * represent the set of addresses that are required.  These values
42  * are used as input to the VL_GetAddrsU RPC which returns a list
43  * of addresses.  For each returned address a bucket in the provided
44  * arrays (serverFlags, serverNumber, serverUUID, serverUnique)
45  * are populated.  The serverFlags array entries are filled with the
46  * 'Flags' value provided as input.  'serverNumber' is the server's
47  * IP address.
48  */
49
50 afs_uint32
51 cm_GetAddrsU(cm_cell_t *cellp, cm_user_t *userp, cm_req_t *reqp,
52              afsUUID *Uuid, afs_int32 Unique, afs_int32 Flags,
53              int *index,
54              afs_int32 serverFlags[],
55              afs_int32 serverNumber[],
56              afsUUID serverUUID[],
57              afs_int32 serverUnique[])
58 {
59     afs_uint32 code = 0;
60     cm_conn_t *connp;
61     struct rx_connection *rxconnp;
62     afs_uint32 * addrp, nentries;
63     afs_int32 unique;
64     bulkaddrs  addrs;
65     ListAddrByAttributes attrs;
66     afsUUID uuid;
67     int i;
68
69     memset(&uuid, 0, sizeof(uuid));
70     memset(&addrs, 0, sizeof(addrs));
71     memset(&attrs, 0, sizeof(attrs));
72
73     attrs.Mask = VLADDR_UUID;
74     attrs.uuid = *Uuid;
75
76     do {
77         code = cm_ConnByMServers(cellp->vlServersp, 0, userp, reqp, &connp);
78         if (code)
79             continue;
80         rxconnp = cm_GetRxConn(connp);
81         code = VL_GetAddrsU(rxconnp, &attrs, &uuid, &unique, &nentries,
82                             &addrs);
83         rx_PutConnection(rxconnp);
84     } while (cm_Analyze(connp, userp, reqp, NULL, cellp, 0, NULL, NULL,
85                         &cellp->vlServersp, NULL, code));
86
87     code = cm_MapVLRPCError(code, reqp);
88
89     if (afsd_logp->enabled) {
90         char uuidstr[128];
91         afsUUID_to_string(Uuid, uuidstr, sizeof(uuidstr));
92
93         if (code)
94             osi_Log2(afsd_logp,
95                      "CALL VL_GetAddrsU serverNumber %s FAILURE, code 0x%x",
96                      osi_LogSaveString(afsd_logp, uuidstr),
97                      code);
98         else
99             osi_Log1(afsd_logp, "CALL VL_GetAddrsU serverNumber %s SUCCESS",
100                      osi_LogSaveString(afsd_logp, uuidstr));
101     }
102
103     if (code)
104         return CM_ERROR_RETRY;
105
106     if (nentries == 0) {
107         code = CM_ERROR_INVAL;
108     } else {
109         addrp = addrs.bulkaddrs_val;
110         for (i = 0; i < nentries && (*index) < NMAXNSERVERS; (*index)++, i++) {
111             serverFlags[*index] = Flags;
112             serverNumber[*index] = addrp[i];
113             serverUUID[*index] = uuid;
114             serverUnique[*index] = unique;
115         }
116     }
117     xdr_free((xdrproc_t) xdr_bulkaddrs, &addrs);
118
119     return code;
120 }