2 * Copyright 2000, International Business Machines Corporation and others.
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
10 /* procedures invoked by the rpc stub */
12 #include <afsconfig.h>
13 #include <afs/param.h>
15 #include <afs/procmgmt.h>
20 #include <afs/afsint.h>
21 #include <afs/prs_fs.h>
25 #include <afs/cellconfig.h>
28 #include <afs/tcdata.h>
29 #include <afs/budb_client.h>
30 #include <afs/bucoord_prototypes.h>
32 #include "error_macros.h"
33 #include "butc_xbsa.h"
34 #include "butc_prototypes.h"
35 #include "butc_internal.h"
37 static int CopyDumpDesc(struct tc_dumpDesc *, tc_dumpArray *);
38 static int CopyRestoreDesc(struct tc_restoreDesc *, tc_restoreArray *);
39 static int CopyTapeSetDesc(struct tc_tapeSet *, struct tc_tapeSet *);
42 callPermitted(struct rx_call *call)
45 * Before this code can be used, the rx connection, on the bucoord side,
46 * must be changed so that it will set up for token passing instead of
47 * using a simple rx connection that, below, returns a value of
48 * RX_SECIDX_NULL from rx_SecurityClassOf.
53 /* -----------------------------
55 * -----------------------------
59 CopyDumpDesc(struct tc_dumpDesc *toDump, tc_dumpArray *fromDump)
61 struct tc_dumpDesc *toPtr, *fromPtr;
65 fromPtr = fromDump->tc_dumpArray_val;
66 for (i = 0; i < fromDump->tc_dumpArray_len; i++) {
67 toPtr->vid = fromPtr->vid;
68 toPtr->vtype = fromPtr->vtype;
69 toPtr->partition = fromPtr->partition;
70 toPtr->date = fromPtr->date;
71 toPtr->cloneDate = fromPtr->cloneDate;
72 toPtr->hostAddr = fromPtr->hostAddr;
73 strcpy(toPtr->name, fromPtr->name);
82 CopyRestoreDesc(struct tc_restoreDesc *toRestore, tc_restoreArray *fromRestore)
84 struct tc_restoreDesc *toPtr, *fromPtr;
88 fromPtr = fromRestore->tc_restoreArray_val;
89 for (i = 0; i < fromRestore->tc_restoreArray_len; i++) {
90 toPtr->flags = fromPtr->flags;
91 toPtr->position = fromPtr->position;
92 strcpy(toPtr->tapeName, fromPtr->tapeName);
93 toPtr->dbDumpId = fromPtr->dbDumpId;
94 toPtr->initialDumpId = fromPtr->initialDumpId;
95 toPtr->origVid = fromPtr->origVid;
96 toPtr->vid = fromPtr->vid;
97 toPtr->partition = fromPtr->partition;
98 toPtr->dumpLevel = fromPtr->dumpLevel;
99 toPtr->hostAddr = fromPtr->hostAddr;
100 strcpy(toPtr->newName, fromPtr->newName);
101 strcpy(toPtr->oldName, fromPtr->oldName);
110 CopyTapeSetDesc(struct tc_tapeSet *toPtr, struct tc_tapeSet *fromPtr)
113 toPtr->id = fromPtr->id;
114 toPtr->maxTapes = fromPtr->maxTapes;
115 toPtr->a = fromPtr->a;
116 toPtr->b = fromPtr->b;
117 strcpy(toPtr->tapeServer, fromPtr->tapeServer);
118 strcpy(toPtr->format, fromPtr->format);
120 toPtr->expDate = fromPtr->expDate;
121 toPtr->expType = fromPtr->expType;
125 /* -------------------------
126 * butc - interface routines - alphabetic order
127 * -------------------------
131 STC_LabelTape(struct rx_call *acid, struct tc_tapeLabel *label, afs_uint32 *taskId)
133 #ifdef AFS_PTHREAD_ENV
135 pthread_attr_t tattr;
140 struct labelTapeIf *ptr;
141 statusP statusPtr = NULL;
146 return (TC_BADTASK); /* LabelTape does not apply if XBSA */
149 if (callPermitted(acid) == 0)
150 return (TC_NOTPERMITTED);
152 ptr = malloc(sizeof(*ptr));
154 ERROR_EXIT(TC_NOMEMORY);
155 memcpy(&ptr->label, label, sizeof(ptr->label));
157 /* set up the status node */
158 *taskId = allocTaskId(); /* for bucoord */
159 ptr->taskId = *taskId;
161 statusPtr = createStatusNode();
163 ERROR_EXIT(TC_INTERNALERROR);
166 statusPtr->taskId = *taskId;
167 statusPtr->lastPolled = time(0);
168 statusPtr->flags &= ~STARTING; /* ok to examine */
169 strncpy(statusPtr->taskName, "Labeltape", sizeof(statusPtr->taskName));
172 /* create the LWP to do the real work behind the scenes */
173 #ifdef AFS_PTHREAD_ENV
174 code = pthread_attr_init(&tattr);
178 code = pthread_attr_setdetachstate(&tattr, PTHREAD_CREATE_DETACHED);
183 code = pthread_create(&pid, &tattr, Labeller, ptr);
184 AFS_SIGSET_RESTORE();
187 LWP_CreateProcess(Labeller, 32768, 1, (void *)ptr, "labeller process",
194 deleteStatusNode(statusPtr);
203 * Tape coordinator server routine to do a dump
207 STC_PerformDump(struct rx_call *rxCallId, struct tc_dumpInterface *tcdiPtr, tc_dumpArray *tc_dumpArrayPtr, afs_int32 *taskId)
209 struct dumpNode *newNode = 0;
210 statusP statusPtr = 0;
211 #ifdef AFS_PTHREAD_ENV
213 pthread_attr_t tattr;
220 if (callPermitted(rxCallId) == 0)
221 return (TC_NOTPERMITTED);
223 /* should be verifying parameter validity */
226 /* this creates a node in list, alots an id for it and prepares it for locking */
227 CreateNode(&newNode);
229 /*set up the parameters in the node, to be used by LWP */
230 strcpy(newNode->dumpSetName, tcdiPtr->dumpName);
232 newNode->dumpName = strdup(tcdiPtr->dumpPath);
233 newNode->volumeSetName = strdup(tcdiPtr->volumeSetName);
235 CopyTapeSetDesc(&(newNode->tapeSetDesc), &tcdiPtr->tapeSet);
237 newNode->dumps = malloc(sizeof(struct tc_dumpDesc) *
238 tc_dumpArrayPtr->tc_dumpArray_len);
239 newNode->arraySize = tc_dumpArrayPtr->tc_dumpArray_len;
240 CopyDumpDesc(newNode->dumps, tc_dumpArrayPtr);
242 newNode->parent = tcdiPtr->parentDumpId;
243 newNode->level = tcdiPtr->dumpLevel;
244 newNode->doAppend = tcdiPtr->doAppend;
247 newNode->doAppend = 0; /* Append flag is ignored if talking to XBSA */
250 /* create the status node */
251 statusPtr = createStatusNode();
253 ERROR_EXIT(TC_INTERNALERROR);
256 statusPtr->taskId = newNode->taskID;
257 statusPtr->lastPolled = time(0);
258 statusPtr->flags &= ~STARTING; /* ok to examine */
259 strncpy(statusPtr->taskName, "Dump", sizeof(statusPtr->taskName));
262 newNode->statusNodePtr = statusPtr;
264 /* create the LWP to do the real work behind the scenes */
265 #ifdef AFS_PTHREAD_ENV
266 code = pthread_attr_init(&tattr);
270 code = pthread_attr_setdetachstate(&tattr, PTHREAD_CREATE_DETACHED);
275 code = pthread_create(&pid, &tattr, Dumper, newNode);
276 AFS_SIGSET_RESTORE();
279 LWP_CreateProcess(Dumper, 32768, 1, (void *)newNode, "dumper process",
285 *taskId = newNode->taskID;
290 deleteStatusNode(statusPtr);
291 FreeNode(newNode->taskID); /* failed to create LWP to do the dump. */
298 STC_PerformRestore(struct rx_call *acid, char *dumpSetName, tc_restoreArray *arestores, afs_int32 *taskID)
300 struct dumpNode *newNode;
303 #ifdef AFS_PTHREAD_ENV
305 pthread_attr_t tattr;
311 if (callPermitted(acid) == 0)
312 return (TC_NOTPERMITTED);
314 /* should verify parameter validity */
316 /* this creates a node in list, alots an id for it and prepares it for locking */
317 CreateNode(&newNode);
319 newNode->restores = malloc(sizeof(struct tc_restoreDesc) *
320 arestores->tc_restoreArray_len);
321 newNode->arraySize = arestores->tc_restoreArray_len;
322 CopyRestoreDesc(newNode->restores, arestores);
323 *taskID = newNode->taskID;
325 /* should log the intent */
327 /* create the status node */
328 statusPtr = createStatusNode();
330 ERROR_EXIT(TC_INTERNALERROR);
333 statusPtr->taskId = newNode->taskID;
334 statusPtr->flags &= ~STARTING; /* ok to examine */
335 statusPtr->lastPolled = time(0);
336 strncpy(statusPtr->taskName, "Restore", sizeof(statusPtr->taskName));
339 newNode->statusNodePtr = statusPtr;
341 /* create the LWP to do the real work behind the scenes */
342 #ifdef AFS_PTHREAD_ENV
343 code = pthread_attr_init(&tattr);
347 code = pthread_attr_setdetachstate(&tattr, PTHREAD_CREATE_DETACHED);
352 code = pthread_create(&pid, &tattr, Restorer, newNode);
353 AFS_SIGSET_RESTORE();
356 LWP_CreateProcess(Restorer, 65368, 1, (void *)newNode,
357 "restorer process", &pid);
363 deleteStatusNode(statusPtr);
364 FreeNode(newNode->taskID); /* failed to create LWP to do the dump. */
371 STC_ReadLabel(struct rx_call *acid, struct tc_tapeLabel *label, afs_uint32 *taskId)
375 memset(label, 0, sizeof(*label));
376 /* Synchronous, so no "real" ID; don't send stack garbage on the wire */
380 return (TC_BADTASK); /* ReadLabel does not apply if XBSA */
383 if (callPermitted(acid) == 0)
384 return (TC_NOTPERMITTED);
386 code = ReadLabel(label); /* Synchronous */
391 * restore the backup database from tape
395 STC_RestoreDb(struct rx_call *rxCall, afs_uint32 *taskId)
397 #ifdef AFS_PTHREAD_ENV
399 pthread_attr_t tattr;
409 return (TC_BADTASK); /* LabelTape does not apply if XBSA */
412 if (callPermitted(rxCall) == 0)
413 return (TC_NOTPERMITTED);
415 *taskId = allocTaskId();
417 /* create the status node */
418 statusPtr = createStatusNode();
420 ERROR_EXIT(TC_INTERNALERROR);
423 statusPtr->taskId = *taskId;
424 statusPtr->flags &= ~STARTING; /* ok to examine */
425 statusPtr->lastPolled = time(0);
426 strncpy(statusPtr->taskName, "RestoreDb", sizeof(statusPtr->taskName));
429 #ifdef AFS_PTHREAD_ENV
430 code = pthread_attr_init(&tattr);
434 code = pthread_attr_setdetachstate(&tattr, PTHREAD_CREATE_DETACHED);
439 code = pthread_create(&pid, &tattr, restoreDbFromTape, (void *)(intptr_t)*taskId);
440 AFS_SIGSET_RESTORE();
443 LWP_CreateProcess(restoreDbFromTape, 32768, 1, (void *)(intptr_t)*taskId,
450 deleteStatusNode(statusPtr);
457 * restore the backup database from tape
461 STC_SaveDb(struct rx_call *rxCall, Date archiveTime, afs_uint32 *taskId)
463 #ifdef AFS_PTHREAD_ENV
465 pthread_attr_t tattr;
470 statusP statusPtr = NULL;
472 struct saveDbIf *ptr;
476 return (TC_BADTASK); /* LabelTape does not apply if XBSA */
479 if (callPermitted(rxCall) == 0)
480 return (TC_NOTPERMITTED);
482 *taskId = allocTaskId();
484 ptr = malloc(sizeof(struct saveDbIf));
486 ERROR_EXIT(TC_NOMEMORY);
487 ptr->archiveTime = archiveTime;
488 ptr->taskId = *taskId;
490 /* create the status node */
491 statusPtr = createStatusNode();
493 ERROR_EXIT(TC_INTERNALERROR);
496 statusPtr->taskId = *taskId;
497 statusPtr->lastPolled = time(0);
498 statusPtr->flags &= ~STARTING; /* ok to examine */
499 strncpy(statusPtr->taskName, "SaveDb", sizeof(statusPtr->taskName));
502 ptr->statusPtr = statusPtr;
504 #ifdef AFS_PTHREAD_ENV
505 code = pthread_attr_init(&tattr);
509 code = pthread_attr_setdetachstate(&tattr, PTHREAD_CREATE_DETACHED);
514 code = pthread_create(&pid, &tattr, saveDbToTape, ptr);
515 AFS_SIGSET_RESTORE();
517 code = LWP_CreateProcess(saveDbToTape, 32768, 1, ptr, "Db save", &pid);
523 deleteStatusNode(statusPtr);
533 * read a dump (maybe more than one tape), and print out a summary
534 * of its contents. If the flag is set, add to the database.
536 * addDbFlag - if set, the information will be added to the database
540 STC_ScanDumps(struct rx_call *acid, afs_int32 addDbFlag, afs_uint32 *taskId)
542 #ifdef AFS_PTHREAD_ENV
544 pthread_attr_t tattr;
549 struct scanTapeIf *ptr;
550 statusP statusPtr = NULL;
555 return (TC_BADTASK); /* ScanDumps does not apply if XBSA */
558 if (callPermitted(acid) == 0)
559 return (TC_NOTPERMITTED);
561 *taskId = allocTaskId();
563 ptr = malloc(sizeof(*ptr));
565 ERROR_EXIT(TC_NOMEMORY);
566 ptr->addDbFlag = addDbFlag;
567 ptr->taskId = *taskId;
569 /* create the status node */
570 statusPtr = createStatusNode();
572 ERROR_EXIT(TC_INTERNALERROR);
575 statusPtr->taskId = *taskId;
576 statusPtr->lastPolled = time(0);
577 statusPtr->flags &= ~STARTING; /* ok to examine */
578 strncpy(statusPtr->taskName, "Scantape", sizeof(statusPtr->taskName));
581 #ifdef AFS_PTHREAD_ENV
582 code = pthread_attr_init(&tattr);
586 code = pthread_attr_setdetachstate(&tattr, PTHREAD_CREATE_DETACHED);
591 code = pthread_create(&pid, &tattr, ScanDumps, ptr);
592 AFS_SIGSET_RESTORE();
595 LWP_CreateProcess(ScanDumps, 32768, 1, ptr, "scandump process", &pid);
601 deleteStatusNode(statusPtr);
610 * return information about the tape coordinator. Currently this
611 * is just the version number of the interface
615 STC_TCInfo(struct rx_call *acid, struct tc_tcInfo *tciptr)
617 if (callPermitted(acid) == 0)
618 return (TC_NOTPERMITTED);
620 tciptr->tcVersion = CUR_BUTC_VERSION;
627 STC_DeleteDump(struct rx_call *acid, afs_uint32 dumpID, afs_uint32 *taskId)
629 afs_int32 code = TC_BADTASK; /* If not compiled -Dxbsa then fail */
631 struct deleteDumpIf *ptr = 0;
632 statusP statusPtr = 0;
633 #ifdef AFS_PTHREAD_ENV
635 pthread_attr_t tattr;
644 return (TC_BADTASK); /* Only do if butc is started as XBSA */
648 if (callPermitted(acid) == 0)
649 return (TC_NOTPERMITTED);
651 ptr = malloc(sizeof(*ptr));
653 ERROR_EXIT(TC_NOMEMORY);
655 *taskId = allocTaskId();
656 ptr->dumpID = dumpID;
657 ptr->taskId = *taskId;
659 statusPtr = createStatusNode();
661 ERROR_EXIT(TC_INTERNALERROR);
664 statusPtr->taskId = *taskId;
665 statusPtr->lastPolled = time(0);
666 statusPtr->flags &= ~STARTING;
667 strncpy(statusPtr->taskName, "DeleteDump", sizeof(statusPtr->taskName));
670 #ifdef AFS_PTHREAD_ENV
671 code = pthread_attr_init(&tattr);
675 code = pthread_attr_setdetachstate(&tattr, PTHREAD_CREATE_DETACHED);
680 code = pthread_create(&pid, &tattr, DeleteDump, ptr);
681 AFS_SIGSET_RESTORE();
684 LWP_CreateProcess(DeleteDump, 32768, 1, ptr, "deletedump process",
691 deleteStatusNode(statusPtr);