Import Upstream version 1.8.5
[hcoop/debian/openafs.git] / src / sys / rmtsysnet.c
1 /*
2 * Copyright 2000, International Business Machines Corporation and others.
3 * All Rights Reserved.
4 *
5 * This software has been released under the terms of the IBM Public
6 * License. For details, see the LICENSE file in the top-level source
7 * directory or online at http://www.openafs.org/dl/license10.html
8 */
9
10 #include <afsconfig.h>
11 #include <afs/param.h>
12
13 #include <roken.h>
14
15 #include <afs/afs_consts.h>
16 #include <afs/vice.h>
17 #include <afs/afsint.h>
18 #include <afs/venus.h>
19 #include <rx/xdr.h>
20
21 #include "rmtsys.h"
22
23
24 /*
25 * We deal with converting pioctl parameters between host and network order.
26 * Painful but somebody has to do this and pioctl is the best place rather than
27 * leaving it to the calling application programs!
28 */
29
30 #define MAXNAME 100
31 #define MAXGCSIZE 16
32
33 struct Acl {
34 int nplus;
35 int nminus;
36 struct AclEntry *pluslist;
37 struct AclEntry *minuslist;
38 };
39
40 struct AclEntry {
41 struct AclEntry *next;
42 char name[MAXNAME];
43 afs_int32 rights;
44 };
45
46 struct ClearToken {
47 afs_int32 AuthHandle;
48 char HandShakeKey[8];
49 afs_int32 ViceId;
50 afs_int32 BeginTimestamp;
51 afs_int32 EndTimestamp;
52 };
53
54 char *
55 RSkipLine(char *astr)
56 {
57 while (*astr != '\n')
58 astr++;
59 astr++;
60 return astr;
61 }
62
63
64 struct Acl *
65 RParseAcl(char *astr)
66 {
67 int nplus, nminus, i, trights;
68 char tname[MAXNAME];
69 struct AclEntry *first, *last, *tl;
70 struct Acl *ta;
71 sscanf(astr, "%d", &nplus);
72 astr = RSkipLine(astr);
73 sscanf(astr, "%d", &nminus);
74 astr = RSkipLine(astr);
75
76 ta = malloc(sizeof(struct Acl));
77 ta->nplus = nplus;
78 ta->nminus = nminus;
79
80 last = 0;
81 first = 0;
82 for (i = 0; i < nplus; i++) {
83 sscanf(astr, "%100s %d", tname, &trights);
84 astr = RSkipLine(astr);
85 tl = malloc(sizeof(struct AclEntry));
86 if (!first)
87 first = tl;
88 strcpy(tl->name, tname);
89 tl->rights = trights;
90 tl->next = 0;
91 if (last)
92 last->next = tl;
93 last = tl;
94 }
95 ta->pluslist = first;
96
97 last = 0;
98 first = 0;
99 for (i = 0; i < nminus; i++) {
100 sscanf(astr, "%100s %d", tname, &trights);
101 astr = RSkipLine(astr);
102 tl = malloc(sizeof(struct AclEntry));
103 if (!first)
104 first = tl;
105 strcpy(tl->name, tname);
106 tl->rights = trights;
107 tl->next = 0;
108 if (last)
109 last->next = tl;
110 last = tl;
111 }
112 ta->minuslist = first;
113
114 return ta;
115 }
116
117
118 void
119 RAclToString(struct Acl *acl, char *mydata, int ntoh_conv)
120 {
121 char tstring[AFS_PIOCTL_MAXSIZE];
122 struct AclEntry *tp;
123
124 /* No conversion needed since they're in network order in the first place */
125 sprintf(mydata, "%d\n%d\n", acl->nplus, acl->nminus);
126 for (tp = acl->pluslist; tp; tp = tp->next) {
127 sprintf(tstring, "%s %d\n", tp->name, tp->rights);
128 strcat(mydata, tstring);
129 }
130 for (tp = acl->minuslist; tp; tp = tp->next) {
131 sprintf(tstring, "%s %d\n", tp->name, tp->rights);
132 strcat(mydata, tstring);
133 }
134 }
135
136
137 /* Free all malloced stuff */
138 void
139 RCleanAcl(struct Acl *aa)
140 {
141 struct AclEntry *te, *ne;
142
143 for (te = aa->pluslist; te; te = ne) {
144 ne = te->next;
145 free(te);
146 }
147 for (te = aa->minuslist; te; te = ne) {
148 ne = te->next;
149 free(te);
150 }
151 free(aa);
152 }
153
154
155 void
156 RFetchVolumeStatus_conversion(char *data, int ntoh_conv)
157 {
158 struct AFSFetchVolumeStatus *status = (AFSFetchVolumeStatus *) data;
159
160 if (ntoh_conv) { /* Network -> Host */
161 status->Vid = ntohl(status->Vid);
162 status->ParentId = ntohl(status->ParentId);
163 #ifdef notdef
164 /* save cycles */
165 status->OnLine = status->OnLine;
166 status->InService = status->InService;
167 status->Blessed = status->Blessed;
168 status->NeedsSalvage = status->NeedsSalvage;
169 #endif
170 status->Type = ntohl(status->Type);
171 status->MinQuota = ntohl(status->MinQuota);
172 status->MaxQuota = ntohl(status->MaxQuota);
173 status->BlocksInUse = ntohl(status->BlocksInUse);
174 status->PartBlocksAvail = ntohl(status->PartBlocksAvail);
175 status->PartMaxBlocks = ntohl(status->PartMaxBlocks);
176 } else { /* Host -> Network */
177 status->Vid = htonl(status->Vid);
178 status->ParentId = htonl(status->ParentId);
179 #ifdef notdef
180 /* save cycles */
181 status->OnLine = status->OnLine;
182 status->InService = status->InService;
183 status->Blessed = status->Blessed;
184 status->NeedsSalvage = status->NeedsSalvage;
185 #endif
186 status->Type = htonl(status->Type);
187 status->MinQuota = htonl(status->MinQuota);
188 status->MaxQuota = htonl(status->MaxQuota);
189 status->BlocksInUse = htonl(status->BlocksInUse);
190 status->PartBlocksAvail = htonl(status->PartBlocksAvail);
191 status->PartMaxBlocks = htonl(status->PartMaxBlocks);
192 }
193 }
194
195 void
196 RClearToken_convert(char *ptr, int ntoh_conv)
197 {
198 struct ClearToken *ticket = (struct ClearToken *)ptr;
199
200 if (ntoh_conv) { /* Network -> host */
201 ticket->AuthHandle = ntohl(ticket->AuthHandle);
202 ticket->ViceId = ntohl(ticket->ViceId);
203 ticket->BeginTimestamp = ntohl(ticket->BeginTimestamp);
204 ticket->EndTimestamp = ntohl(ticket->EndTimestamp);
205 } else { /* Host -> Network */
206 ticket->AuthHandle = htonl(ticket->AuthHandle);
207 ticket->ViceId = htonl(ticket->ViceId);
208 ticket->BeginTimestamp = htonl(ticket->BeginTimestamp);
209 ticket->EndTimestamp = htonl(ticket->EndTimestamp);
210 }
211 }
212
213 void
214 inparam_conversion(afs_int32 cmd, char *buffer, afs_int32 ntoh_conv)
215 {
216 struct Acl *acl;
217 afs_int32 *lptr, i;
218 char *ptr;
219
220 switch (cmd & 0xffff) {
221 case VIOCSETAL & 0xffff:
222 acl = RParseAcl(buffer);
223 RAclToString(acl, buffer, ntoh_conv);
224 RCleanAcl(acl);
225 break;
226 case VIOCSETTOK & 0xffff:
227 lptr = (afs_int32 *) buffer;
228 /* i is sizeof of the secret ticket */
229 if (ntoh_conv) {
230 i = ntohl(*lptr);
231 *lptr = i;
232 } else {
233 i = *lptr;
234 *lptr = htonl(i);
235 }
236 lptr++;
237 ptr = (char *)lptr;
238 ptr += i; /* skip over the ticket */
239 lptr = (afs_int32 *) ptr;
240 /* i is now size of the clear token */
241 if (ntoh_conv) {
242 i = ntohl(*lptr);
243 *lptr = i;
244 } else {
245 i = *lptr;
246 *lptr = htonl(i);
247 }
248 lptr++;
249 ptr = (char *)lptr;
250 RClearToken_convert(ptr, ntoh_conv);
251 ptr += i; /* sizeof(struct ClearToken) */
252 lptr = (afs_int32 *) ptr;
253 if (ntoh_conv)
254 *lptr = ntohl(*lptr);
255 else
256 *lptr = htonl(*lptr);
257 lptr++; /* primary flag */
258 break;
259 case VIOCSETVOLSTAT & 0xffff:
260 RFetchVolumeStatus_conversion(buffer, ntoh_conv);
261 break;
262 case VIOCGETTOK & 0xffff:
263 case VIOCCKSERV & 0xffff:
264 case VIOCACCESS & 0xffff:
265 case VIOCSETCACHESIZE & 0xffff:
266 case VIOCGETCELL & 0xffff:
267 case VIOC_AFS_MARINER_HOST & 0xffff:
268 case VIOC_VENUSLOG & 0xffff:
269 case VIOC_AFS_SYSNAME & 0xffff:
270 case VIOC_EXPORTAFS & 0xffff:
271 lptr = (afs_int32 *) buffer;
272 if (ntoh_conv)
273 *lptr = ntohl(*lptr);
274 else
275 *lptr = htonl(*lptr);
276 break;
277 case VIOC_SETCELLSTATUS & 0xffff:
278 lptr = (afs_int32 *) buffer;
279 if (ntoh_conv)
280 *lptr = ntohl(*lptr);
281 else
282 *lptr = htonl(*lptr);
283 lptr++;
284 if (ntoh_conv)
285 *lptr = ntohl(*lptr);
286 else
287 *lptr = htonl(*lptr);
288 break;
289 case VIOCGETAL & 0xffff:
290 case VIOCGETVOLSTAT & 0xffff:
291 case VIOCGETCACHEPARMS & 0xffff:
292 case VIOCFLUSH & 0xffff:
293 case VIOCSTAT & 0xffff:
294 case VIOCUNLOG & 0xffff:
295 case VIOCCKBACK & 0xffff:
296 case VIOCCKCONN & 0xffff:
297 case VIOCGETTIME & 0xffff: /* Obsolete */
298 case VIOCWHEREIS & 0xffff:
299 case VIOCPREFETCH & 0xffff:
300 case VIOCNOP & 0xffff: /* Obsolete */
301 case VIOCENGROUP & 0xffff: /* Obsolete */
302 case VIOCDISGROUP & 0xffff: /* Obsolete */
303 case VIOCLISTGROUPS & 0xffff: /* Obsolete */
304 case VIOCUNPAG & 0xffff:
305 case VIOCWAITFOREVER & 0xffff: /* Obsolete */
306 case VIOCFLUSHCB & 0xffff:
307 case VIOCNEWCELL & 0xffff:
308 case VIOC_AFS_DELETE_MT_PT & 0xffff:
309 case VIOC_AFS_STAT_MT_PT & 0xffff:
310 case VIOC_FILE_CELL_NAME & 0xffff:
311 case VIOC_GET_WS_CELL & 0xffff:
312 case VIOC_GET_PRIMARY_CELL & 0xffff:
313 case VIOC_GETCELLSTATUS & 0xffff:
314 case VIOC_FLUSHVOLUME & 0xffff:
315 case VIOCGETFID & 0xffff: /* nothing yet */
316 break;
317 default:
318 /* Note that new pioctls are supposed to be in network order! */
319 break;
320 }
321 }
322
323
324 void
325 outparam_conversion(afs_int32 cmd, char *buffer, afs_int32 ntoh_conv)
326 {
327 struct Acl *acl;
328 afs_int32 *lptr, i;
329 char *ptr;
330
331 switch (cmd & 0xffff) {
332 case VIOCGETAL & 0xffff:
333 acl = RParseAcl(buffer);
334 RAclToString(acl, buffer, ntoh_conv);
335 RCleanAcl(acl);
336 break;
337 case VIOCGETVOLSTAT & 0xffff:
338 RFetchVolumeStatus_conversion(buffer, ntoh_conv);
339 break;
340 case VIOCSETVOLSTAT & 0xffff:
341 RFetchVolumeStatus_conversion(buffer, ntoh_conv);
342 break;
343 case VIOCGETTOK & 0xffff:
344 lptr = (afs_int32 *) buffer;
345 /* i is set to sizeof secret ticket */
346 if (ntoh_conv) {
347 i = ntohl(*lptr);
348 *lptr = i;
349 } else {
350 i = *lptr;
351 *lptr = htonl(i);
352 }
353 lptr++;
354 ptr = (char *)lptr;
355 ptr += i; /* skip over the ticket */
356 lptr = (afs_int32 *) ptr;
357 /* i is set to sizeof clear ticket */
358 if (ntoh_conv) {
359 i = ntohl(*lptr);
360 *lptr = i;
361 } else {
362 i = *lptr;
363 *lptr = htonl(i);
364 }
365 lptr++;
366 ptr = (char *)lptr;
367 RClearToken_convert(ptr, ntoh_conv);
368 ptr += i; /* sizeof(struct ClearToken) */
369 lptr = (afs_int32 *) ptr;
370 if (ntoh_conv)
371 *lptr = ntohl(*lptr);
372 else
373 *lptr = htonl(*lptr);
374 lptr++; /* primary flag */
375 break;
376 case VIOCCKCONN & 0xffff:
377 case VIOC_AFS_MARINER_HOST & 0xffff:
378 case VIOC_VENUSLOG & 0xffff:
379 case VIOC_GETCELLSTATUS & 0xffff:
380 case VIOC_AFS_SYSNAME & 0xffff:
381 case VIOC_EXPORTAFS & 0xffff:
382 lptr = (afs_int32 *) buffer;
383 if (ntoh_conv)
384 *lptr = ntohl(*lptr);
385 else
386 *lptr = htonl(*lptr);
387 break;
388 case VIOCGETCACHEPARMS & 0xffff:
389 lptr = (afs_int32 *) buffer;
390 for (i = 0; i < MAXGCSIZE; i++, lptr++) {
391 if (ntoh_conv)
392 *lptr = ntohl(*lptr);
393 else
394 *lptr = htonl(*lptr);
395 }
396 break;
397 case VIOCUNLOG & 0xffff:
398 case VIOCCKSERV & 0xffff: /* Already in network order */
399 case VIOCCKBACK & 0xffff:
400 case VIOCGETTIME & 0xffff: /* Obsolete */
401 case VIOCWHEREIS & 0xffff: /* Already in network order */
402 case VIOCPREFETCH & 0xffff:
403 case VIOCNOP & 0xffff: /* Obsolete */
404 case VIOCENGROUP & 0xffff: /* Obsolete */
405 case VIOCDISGROUP & 0xffff: /* Obsolete */
406 case VIOCLISTGROUPS & 0xffff: /* Obsolete */
407 case VIOCACCESS & 0xffff:
408 case VIOCUNPAG & 0xffff:
409 case VIOCWAITFOREVER & 0xffff: /* Obsolete */
410 case VIOCSETCACHESIZE & 0xffff:
411 case VIOCFLUSHCB & 0xffff:
412 case VIOCNEWCELL & 0xffff:
413 case VIOCGETCELL & 0xffff: /* Already in network order */
414 case VIOC_AFS_DELETE_MT_PT & 0xffff:
415 case VIOC_AFS_STAT_MT_PT & 0xffff:
416 case VIOC_FILE_CELL_NAME & 0xffff: /* no need to convert */
417 case VIOC_GET_WS_CELL & 0xffff: /* no need to convert */
418 case VIOCGETFID & 0xffff: /* nothing yet */
419 case VIOCSETAL & 0xffff:
420 case VIOCFLUSH & 0xffff:
421 case VIOCSTAT & 0xffff:
422 case VIOCSETTOK & 0xffff:
423 case VIOC_GET_PRIMARY_CELL & 0xffff: /* The cell is returned here */
424 case VIOC_SETCELLSTATUS & 0xffff:
425 case VIOC_FLUSHVOLUME & 0xffff:
426 break;
427 default:
428 /* Note that new pioctls are supposed to be in network order! */
429 break;
430 }
431 }