Import Upstream version 1.8.5
[hcoop/debian/openafs.git] / src / libadmin / bos / afs_bosAdmin.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 #include <afs/stds.h>
13
14 #include <roken.h>
15
16 #include <rx/rx.h>
17 #include <rx/rxstat.h>
18 #include <afs/afs_AdminErrors.h>
19 #include <afs/afs_utilAdmin.h>
20 #include <afs/bosint.h>
21 #include <afs/bnode.h>
22 #include <afs/ktime.h>
23 #include <afs/dirpath.h>
24
25 #include "afs_bosAdmin.h"
26 #include "../adminutil/afs_AdminInternal.h"
27
28 typedef struct bos_server {
29 int begin_magic;
30 int is_valid;
31 struct rx_connection *server;
32 struct rx_connection *server_encrypt;
33 struct rx_connection *server_stats;
34 int end_magic;
35 } bos_server_t, *bos_server_p;
36
37 /*
38 * isValidServerHandle - validate a bos_server_p.
39 *
40 * PARAMETERS
41 *
42 * IN serverHandle - the handle to validate
43 *
44 * LOCKS
45 *
46 * No locks are obtained or released by this function
47 *
48 * RETURN CODES
49 *
50 * Returns != 0 upon successful completion.
51 */
52
53 int
54 isValidServerHandle(const bos_server_p serverHandle, afs_status_p st)
55 {
56 int rc = 0;
57 afs_status_t tst = 0;
58
59 if (serverHandle == NULL) {
60 tst = ADMBOSSERVERHANDLENULL;
61 goto fail_IsValidServerHandle;
62 }
63
64 if ((serverHandle->begin_magic != BEGIN_MAGIC)
65 || (serverHandle->end_magic != END_MAGIC)) {
66 tst = ADMBOSSERVERHANDLEBADMAGIC;
67 goto fail_IsValidServerHandle;
68 }
69
70 if (serverHandle->is_valid == 0) {
71 tst = ADMBOSSERVERHANDLEINVALID;
72 goto fail_IsValidServerHandle;
73 }
74
75 if (serverHandle->server == NULL) {
76 tst = ADMBOSSERVERHANDLENOSERVER;
77 goto fail_IsValidServerHandle;
78 }
79
80 if (serverHandle->server_encrypt == NULL) {
81 tst = ADMBOSSERVERHANDLENOSERVER;
82 goto fail_IsValidServerHandle;
83 }
84 rc = 1;
85
86 fail_IsValidServerHandle:
87
88 if (st != NULL) {
89 *st = tst;
90 }
91 return rc;
92 }
93
94 /*
95 * IsValidCellHandle - verify that a cell handle can be used to make bos
96 * requests.
97 *
98 * PARAMETERS
99 *
100 * IN cellHandle - the cellHandle to be validated.
101 *
102 * LOCKS
103 *
104 * No locks are obtained or released by this function
105 *
106 * RETURN CODES
107 *
108 * Returns != 0 upon successful completion.
109 */
110
111 static int
112 IsValidCellHandle(afs_cell_handle_p cellHandle, afs_status_p st)
113 {
114 int rc = 0;
115 afs_status_t tst = 0;
116
117 if (!CellHandleIsValid((void *)cellHandle, &tst)) {
118 goto fail_IsValidCellHandle;
119 }
120
121 if (cellHandle->tokens == NULL) {
122 tst = ADMBOSCELLHANDLENOTOKENS;
123 goto fail_IsValidCellHandle;
124 }
125 rc = 1;
126
127 fail_IsValidCellHandle:
128
129 if (st != NULL) {
130 *st = tst;
131 }
132 return rc;
133 }
134
135 /*
136 * bos_ServerOpen - open a bos server for work.
137 *
138 * PARAMETERS
139 *
140 * IN cellHandle - a previously opened cellHandle.
141 *
142 * IN serverName - the name of the machine that houses the bosserver of
143 * interest.
144 *
145 * OUT serverHandleP - upon successful completion, this void pointer
146 * will point to a valid server handle for use in future operations.
147 *
148 * LOCKS
149 *
150 * No locks are obtained or released by this function
151 *
152 * RETURN CODES
153 *
154 * Returns != 0 upon successful completion.
155 */
156
157 int ADMINAPI
158 bos_ServerOpen(const void *cellHandle, const char *serverName,
159 void **serverHandleP, afs_status_p st)
160 {
161 int rc = 0;
162 afs_status_t tst = 0;
163 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
164 bos_server_p bos_server = calloc(1, sizeof(bos_server_t));
165 int serverAddress;
166
167 /*
168 * Validate parameters
169 */
170
171 if (!IsValidCellHandle(c_handle, &tst)) {
172 goto fail_bos_ServerOpen;
173 }
174
175 if ((serverName == NULL) || (*serverName == 0)) {
176 tst = ADMBOSSERVERNAMENULL;
177 goto fail_bos_ServerOpen;
178 }
179
180 if (serverHandleP == NULL) {
181 tst = ADMBOSSERVERHANDLEPNULL;
182 goto fail_bos_ServerOpen;
183 }
184
185 if (util_AdminServerAddressGetFromName(serverName, &serverAddress, &tst)
186 == 0) {
187 goto fail_bos_ServerOpen;
188 }
189
190 if (bos_server == NULL) {
191 tst = ADMNOMEM;
192 goto fail_bos_ServerOpen;
193 }
194
195 bos_server->server =
196 rx_GetCachedConnection(htonl(serverAddress), htons(AFSCONF_NANNYPORT),
197 1,
198 c_handle->tokens->afs_sc[c_handle->tokens->
199 sc_index],
200 c_handle->tokens->sc_index);
201
202 bos_server->server_encrypt =
203 rx_GetCachedConnection(htonl(serverAddress), htons(AFSCONF_NANNYPORT),
204 1,
205 c_handle->tokens->afs_encrypt_sc[c_handle->
206 tokens->
207 sc_index],
208 c_handle->tokens->sc_index);
209
210 bos_server->server_stats =
211 rx_GetCachedConnection(htonl(serverAddress), htons(AFSCONF_NANNYPORT),
212 RX_STATS_SERVICE_ID,
213 c_handle->tokens->afs_sc[c_handle->tokens->
214 sc_index],
215 c_handle->tokens->sc_index);
216
217 if ((bos_server->server == NULL) || (bos_server->server_encrypt == NULL)) {
218 tst = ADMBOSSERVERNOCONNECTION;
219 goto fail_bos_ServerOpen;
220 }
221
222 bos_server->begin_magic = BEGIN_MAGIC;
223 bos_server->is_valid = 1;
224 bos_server->end_magic = END_MAGIC;
225
226 *serverHandleP = (void *)bos_server;
227 rc = 1;
228
229 fail_bos_ServerOpen:
230
231 if ((rc == 0) && (bos_server != NULL)) {
232 if (bos_server->server) {
233 rx_ReleaseCachedConnection(bos_server->server);
234 }
235 if (bos_server->server_encrypt) {
236 rx_ReleaseCachedConnection(bos_server->server_encrypt);
237 }
238 free(bos_server);
239 }
240
241 if (st != NULL) {
242 *st = tst;
243 }
244 return rc;
245 }
246
247 /*
248 * bos_ServerClose - close a bos server handle
249 *
250 * PARAMETERS
251 *
252 * IN serverHandle - a bos server handle previously returned by bos_ServerOpen
253 *
254 * LOCKS
255 *
256 * No locks are obtained or released by this function
257 *
258 * RETURN CODES
259 *
260 * Returns != 0 upon successful completion.
261 */
262
263 int ADMINAPI
264 bos_ServerClose(const void *serverHandle, afs_status_p st)
265 {
266 int rc = 0;
267 afs_status_t tst = 0;
268 bos_server_p b_handle = (bos_server_p) serverHandle;
269
270 if (isValidServerHandle(b_handle, &tst)) {
271 rx_ReleaseCachedConnection(b_handle->server);
272 b_handle->is_valid = 0;
273 free(b_handle);
274 rc = 1;
275 }
276
277 if (st != NULL) {
278 *st = tst;
279 }
280 return rc;
281 }
282
283 /*
284 * bos_ProcessCreate - create a new process to run at a bos server.
285 *
286 * PARAMETERS
287 *
288 * IN serverHandle - a previously opened serverHandle.
289 *
290 * IN processName - the name of the process to create.
291 *
292 * IN processType - the type of process to create.
293 *
294 * IN process - the path to the process binary at the bos server.
295 *
296 * IN cronTime - the time specification for cron processes.
297 *
298 * IN notifier - the path to the notifier binary at the bos server.
299 *
300 * LOCKS
301 *
302 * No locks are obtained or released by this function
303 *
304 * RETURN CODES
305 *
306 * Returns != 0 upon successful completion.
307 */
308
309 /*
310 * CAUTION - this list must match bos_ProcessType_t definition
311 */
312
313 static char *processTypes[] = { "simple", "fs", "cron", 0 };
314
315 int ADMINAPI
316 bos_ProcessCreate(const void *serverHandle, char *processName,
317 bos_ProcessType_t processType, char *process,
318 char *cronTime, char *notifier, afs_status_p st)
319 {
320 int rc = 0;
321 afs_status_t tst = 0;
322 bos_server_p b_handle = (bos_server_p) serverHandle;
323
324 if (!isValidServerHandle(b_handle, &tst)) {
325 goto fail_bos_ProcessCreate;
326 }
327
328 if (processType == BOS_PROCESS_FS) {
329 tst = ADMBOSPROCESSCREATEBADTYPE;
330 goto fail_bos_ProcessCreate;
331 }
332
333 if ((processName == NULL) || (*processName == 0)) {
334 tst = ADMBOSPROCESSNAMENULL;
335 goto fail_bos_ProcessCreate;
336 }
337
338 if ((process == NULL) || (*process == 0)) {
339 tst = ADMBOSPROCESSNULL;
340 goto fail_bos_ProcessCreate;
341 }
342
343 if ((processType == BOS_PROCESS_CRON) && (cronTime == NULL)) {
344 tst = ADMBOSCRONTIMENULL;
345 goto fail_bos_ProcessCreate;
346 }
347
348 if ((processType == BOS_PROCESS_SIMPLE) && (cronTime != NULL)) {
349 tst = ADMBOSCRONTIMENOTNULL;
350 goto fail_bos_ProcessCreate;
351 }
352
353 tst =
354 BOZO_CreateBnode(b_handle->server, processTypes[processType],
355 processName, process, (cronTime) ? cronTime : "", "",
356 "", "", (notifier) ? notifier : NONOTIFIER);
357 if (tst == 0) {
358 rc = 1;
359 }
360
361 fail_bos_ProcessCreate:
362
363 if (st != NULL) {
364 *st = tst;
365 }
366 return rc;
367 }
368
369 /*
370 * bos_FSProcessCreate - create the fs group of processes at the boserver.
371 *
372 * PARAMETERS
373 *
374 * IN serverHandle - a previously opened serverHandle.
375 *
376 * IN processName - the name of the process to create.
377 *
378 * IN fileserverPath - the path to the fileserver binary at the bos server.
379 *
380 * IN volserverPath - the path to the volserver binary at the bos server.
381 *
382 * IN salvagerPath - the path to the salvager binary at the bos server.
383 *
384 * IN notifier - the path to the notifier binary at the bos server.
385 *
386 * LOCKS
387 *
388 * No locks are obtained or released by this function
389 *
390 * RETURN CODES
391 *
392 * Returns != 0 upon successful completion.
393 */
394
395 int ADMINAPI
396 bos_FSProcessCreate(const void *serverHandle, char *processName,
397 char *fileserverPath, char *volserverPath,
398 char *salvagerPath, char *notifier,
399 afs_status_p st)
400 {
401 int rc = 0;
402 afs_status_t tst = 0;
403 bos_server_p b_handle = (bos_server_p) serverHandle;
404
405 if (!isValidServerHandle(b_handle, &tst)) {
406 goto fail_bos_ProcessCreate;
407 }
408
409 if ((processName == NULL) || (*processName == 0)) {
410 tst = ADMBOSPROCESSNAMENULL;
411 goto fail_bos_ProcessCreate;
412 }
413
414 if ((fileserverPath == NULL) || (*fileserverPath == 0)) {
415 tst = ADMBOSFILESERVERPATHNULL;
416 goto fail_bos_ProcessCreate;
417 }
418
419 if ((volserverPath == NULL) || (*volserverPath == 0)) {
420 tst = ADMBOSVOLSERVERPATHNULL;
421 goto fail_bos_ProcessCreate;
422 }
423
424 if ((salvagerPath == NULL) || (*salvagerPath == 0)) {
425 tst = ADMBOSSALVAGERPATHNULL;
426 goto fail_bos_ProcessCreate;
427 }
428
429 tst =
430 BOZO_CreateBnode(b_handle->server, processTypes[BOS_PROCESS_FS],
431 processName, fileserverPath, volserverPath,
432 salvagerPath, "", "",
433 (notifier) ? notifier : NONOTIFIER);
434 if (tst == 0) {
435 rc = 1;
436 }
437
438 fail_bos_ProcessCreate:
439
440 if (st != NULL) {
441 *st = tst;
442 }
443 return rc;
444 }
445
446 /*
447 * bos_ProcessDelete - delete an existing process at a bos server.
448 *
449 * PARAMETERS
450 *
451 * IN serverHandle - a previously opened serverHandle.
452 *
453 * IN processName - the name of the process to delete.
454 *
455 * LOCKS
456 *
457 * No locks are obtained or released by this function
458 *
459 * RETURN CODES
460 *
461 * Returns != 0 upon successful completion.
462 */
463
464 int ADMINAPI
465 bos_ProcessDelete(const void *serverHandle, char *processName,
466 afs_status_p st)
467 {
468 int rc = 0;
469 afs_status_t tst = 0;
470 bos_server_p b_handle = (bos_server_p) serverHandle;
471
472 if (!isValidServerHandle(b_handle, &tst)) {
473 goto fail_bos_ProcessDelete;
474 }
475
476 if ((processName == NULL) || (*processName == 0)) {
477 tst = ADMBOSPROCESSNAMENULL;
478 goto fail_bos_ProcessDelete;
479 }
480
481 tst = BOZO_DeleteBnode(b_handle->server, processName);
482
483 if (tst == 0) {
484 rc = 1;
485 }
486
487 fail_bos_ProcessDelete:
488
489 if (st != NULL) {
490 *st = tst;
491 }
492 return rc;
493 }
494
495 /*
496 * bos_ProcessExecutionStateGet - get the current execution state of a
497 * process
498 *
499 * PARAMETERS
500 *
501 * IN serverHandle - a previously opened serverHandle.
502 *
503 * IN processName - the name of the process to retrieve.
504 *
505 * OUT processStatusP - upon successful completion the process execution state
506 *
507 * OUT auxiliaryProcessStatus - set to point to aux proc status if available.
508 * Pass a pointer to an char array at least BOS_MAX_NAME_LEN long.
509 *
510 * LOCKS
511 *
512 * No locks are obtained or released by this function
513 *
514 * RETURN CODES
515 *
516 * Returns != 0 upon successful completion.
517 */
518
519 int ADMINAPI
520 bos_ProcessExecutionStateGet(const void *serverHandle,
521 char *processName,
522 bos_ProcessExecutionState_p processStatusP,
523 char *auxiliaryProcessStatus, afs_status_p st)
524 {
525 int rc = 0;
526 afs_status_t tst = 0;
527 bos_server_p b_handle = (bos_server_p) serverHandle;
528 afs_int32 state;
529
530 if (!isValidServerHandle(b_handle, &tst)) {
531 goto fail_bos_ProcessExecutionStateGet;
532 }
533
534 if ((processName == NULL) || (*processName == 0)) {
535 tst = ADMBOSPROCESSNAMENULL;
536 goto fail_bos_ProcessExecutionStateGet;
537 }
538
539 if (processStatusP == NULL) {
540 tst = ADMBOSPROCESSSTATUSPNULL;
541 goto fail_bos_ProcessExecutionStateGet;
542 }
543
544 if (auxiliaryProcessStatus == NULL) {
545 tst = ADMBOSAUXILIARYPROCESSSTATUSNULL;
546 goto fail_bos_ProcessExecutionStateGet;
547 }
548
549 tst =
550 BOZO_GetStatus(b_handle->server, processName, &state,
551 &auxiliaryProcessStatus);
552
553 if (tst != 0) {
554 goto fail_bos_ProcessExecutionStateGet;
555 }
556
557 *processStatusP = (bos_ProcessExecutionState_t) state;
558 rc = 1;
559
560 fail_bos_ProcessExecutionStateGet:
561
562 if (st != NULL) {
563 *st = tst;
564 }
565 return rc;
566 }
567
568 /*
569 * SetExecutionState - set the execution state of a process
570 *
571 * PARAMETERS
572 *
573 * IN serverHandle - a previously opened serverHandle.
574 *
575 * IN processName - the name of the process to modify.
576 *
577 * IN processStatus - the new process state.
578 *
579 * IN func - the function to call to set the status.
580 *
581 * LOCKS
582 *
583 * No locks are obtained or released by this function
584 *
585 * RETURN CODES
586 *
587 * Returns != 0 upon successful completion.
588 */
589
590 static int
591 SetExecutionState(const void *serverHandle, const char *processName,
592 const bos_ProcessExecutionState_t processStatus,
593 int (*func) (struct rx_connection *, const char *,
594 afs_int32), afs_status_p st)
595 {
596 int rc = 0;
597 afs_status_t tst = 0;
598 bos_server_p b_handle = (bos_server_p) serverHandle;
599 afs_int32 state;
600
601 if (!isValidServerHandle(b_handle, &tst)) {
602 goto fail_SetExecutionState;
603 }
604
605 if ((processName == NULL) || (*processName == 0)) {
606 tst = ADMBOSPROCESSNAMENULL;
607 goto fail_SetExecutionState;
608 }
609
610 if ((processStatus != BOS_PROCESS_STOPPED)
611 && (processStatus != BOS_PROCESS_RUNNING)) {
612 tst = ADMBOSPROCESSSTATUSSET;
613 goto fail_SetExecutionState;
614 }
615
616 state = (afs_int32) processStatus;
617
618 tst = func(b_handle->server, (char *)processName, state);
619
620 if (tst == 0) {
621 rc = 1;
622 }
623
624 fail_SetExecutionState:
625
626 if (st != NULL) {
627 *st = tst;
628 }
629 return rc;
630 }
631
632 /*
633 * bos_ProcessExecutionStateSet - set the execution state of a process
634 *
635 * PARAMETERS
636 *
637 * IN serverHandle - a previously opened serverHandle.
638 *
639 * IN processName - the name of the process to modify.
640 *
641 * IN processStatus - the new process state.
642 *
643 * LOCKS
644 *
645 * No locks are obtained or released by this function
646 *
647 * RETURN CODES
648 *
649 * Returns != 0 upon successful completion.
650 */
651
652 int ADMINAPI
653 bos_ProcessExecutionStateSet(const void *serverHandle,
654 const char *processName,
655 const bos_ProcessExecutionState_t processStatus,
656 afs_status_p st)
657 {
658 return SetExecutionState(serverHandle, processName, processStatus,
659 BOZO_SetStatus, st);
660 }
661
662 /*
663 * bos_ProcessExecutionStateSetTemporary - set the execution state of a process
664 * temporarily
665 *
666 * PARAMETERS
667 *
668 * IN serverHandle - a previously opened serverHandle.
669 *
670 * IN processName - the name of the process to modify.
671 *
672 * IN processStatus - the new process state.
673 *
674 * LOCKS
675 *
676 * No locks are obtained or released by this function
677 *
678 * RETURN CODES
679 *
680 * Returns != 0 upon successful completion.
681 */
682
683 int ADMINAPI
684 bos_ProcessExecutionStateSetTemporary(const void *serverHandle,
685 char *processName,
686 bos_ProcessExecutionState_t
687 processStatus, afs_status_p st)
688 {
689 return SetExecutionState(serverHandle, processName, processStatus,
690 BOZO_SetTStatus, st);
691 }
692
693 /*
694 * The iterator functions and data for the process name retrieval functions
695 */
696
697 typedef struct process_name_get {
698 int next;
699 struct rx_connection *server;
700 char process[CACHED_ITEMS][BOS_MAX_NAME_LEN];
701 } process_name_get_t, *process_name_get_p;
702
703 static int
704 GetProcessNameRPC(void *rpc_specific, int slot, int *last_item,
705 int *last_item_contains_data, afs_status_p st)
706 {
707 int rc = 0;
708 afs_status_t tst = 0;
709 process_name_get_p proc = (process_name_get_p) rpc_specific;
710 char *ptr = (char *)&proc->process[slot];
711
712 tst = BOZO_EnumerateInstance(proc->server, proc->next++, &ptr);
713
714 if (tst == 0) {
715 rc = 1;
716 } else if (tst == BZDOM) {
717 tst = 0;
718 rc = 1;
719 *last_item = 1;
720 *last_item_contains_data = 0;
721 }
722
723 if (st != NULL) {
724 *st = tst;
725 }
726 return rc;
727 }
728
729 static int
730 GetProcessNameFromCache(void *rpc_specific, int slot, void *dest,
731 afs_status_p st)
732 {
733 int rc = 0;
734 afs_status_t tst = 0;
735 process_name_get_p proc = (process_name_get_p) rpc_specific;
736
737 strcpy((char *)dest, (char *)&proc->process[slot]);
738 rc = 1;
739
740 if (st != NULL) {
741 *st = tst;
742 }
743 return rc;
744 }
745
746 /*
747 * bos_ProcessNameGetBegin - begin iterating over the list of processes
748 * at a particular bos server.
749 *
750 * PARAMETERS
751 *
752 * IN serverHandle - a previously opened serverHandle.
753 *
754 * OUT iter - an iterator that can be passed to bos_ProcessNameGetNext
755 * to retrieve the process names.
756 *
757 * LOCKS
758 *
759 * No locks are obtained or released by this function
760 *
761 * RETURN CODES
762 *
763 * Returns != 0 upon successful completion.
764 *
765 */
766
767 int ADMINAPI
768 bos_ProcessNameGetBegin(const void *serverHandle, void **iterationIdP,
769 afs_status_p st)
770 {
771 int rc = 0;
772 afs_status_t tst = 0;
773 bos_server_p b_handle = (bos_server_p) serverHandle;
774 afs_admin_iterator_p iter = malloc(sizeof(afs_admin_iterator_t));
775 process_name_get_p proc = malloc(sizeof(process_name_get_t));
776
777 if (!isValidServerHandle(b_handle, &tst)) {
778 goto fail_bos_ProcessNameGetBegin;
779 }
780
781 if (iterationIdP == NULL) {
782 tst = ADMITERATIONIDPNULL;
783 goto fail_bos_ProcessNameGetBegin;
784 }
785
786 if ((iter == NULL) || (proc == NULL)) {
787 tst = ADMNOMEM;
788 goto fail_bos_ProcessNameGetBegin;
789 }
790
791 proc->next = 0;
792 proc->server = b_handle->server;
793
794 if (IteratorInit
795 (iter, (void *)proc, GetProcessNameRPC, GetProcessNameFromCache, NULL,
796 NULL, &tst)) {
797 *iterationIdP = (void *)iter;
798 } else {
799 goto fail_bos_ProcessNameGetBegin;
800 }
801 rc = 1;
802
803 fail_bos_ProcessNameGetBegin:
804
805 if (rc == 0) {
806 if (iter != NULL) {
807 free(iter);
808 }
809 if (proc != NULL) {
810 free(proc);
811 }
812 }
813
814 if (st != NULL) {
815 *st = tst;
816 }
817 return rc;
818 }
819
820 /*
821 * bos_ProcessNameGetNext - retrieve the next process name from the bos server.
822 *
823 * PARAMETERS
824 *
825 * IN iterationId - an iterator previously returned by bos_ProcessNameGetBegin
826 *
827 * OUT processName - upon successful completion contains the next process name
828 * retrieved from the server.
829 *
830 * LOCKS
831 *
832 * No locks are obtained or released by this function
833 *
834 * RETURN CODES
835 *
836 * Returns != 0 upon successful completion.
837 *
838 */
839
840 int ADMINAPI
841 bos_ProcessNameGetNext(const void *iterationId, char *processName,
842 afs_status_p st)
843 {
844 int rc = 0;
845 afs_status_t tst = 0;
846 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
847
848 if (processName == NULL) {
849 tst = ADMBOSPROCESSNAMENULL;
850 goto fail_bos_ProcessNameGetNext;
851 }
852
853 if (iterationId == NULL) {
854 tst = ADMITERATIONIDPNULL;
855 goto fail_bos_ProcessNameGetNext;
856 }
857
858 rc = IteratorNext(iter, (void *)processName, &tst);
859
860 fail_bos_ProcessNameGetNext:
861
862 if (st != NULL) {
863 *st = tst;
864 }
865 return rc;
866 }
867
868 /*
869 * bos_ProcessNameGetDone - finish using a process name iterator.
870 *
871 * PARAMETERS
872 *
873 * IN iterationId - an iterator previously returned by bos_ProcessNameGetBegin
874 *
875 * LOCKS
876 *
877 * No locks are obtained or released by this function
878 *
879 * RETURN CODES
880 *
881 * Returns != 0 upon successful completion.
882 *
883 */
884
885 int ADMINAPI
886 bos_ProcessNameGetDone(const void *iterationId, afs_status_p st)
887 {
888 int rc = 0;
889 afs_status_t tst = 0;
890 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
891
892 if (iterationId == NULL) {
893 tst = ADMITERATIONIDPNULL;
894 goto fail_bos_ProcessNameGetDone;
895 }
896
897 rc = IteratorDone(iter, &tst);
898
899 fail_bos_ProcessNameGetDone:
900
901 if (st != NULL) {
902 *st = tst;
903 }
904 return rc;
905 }
906
907 /*
908 * bos_ProcessInfoGet - get information about a single process
909 *
910 * PARAMETERS
911 *
912 * IN serverHandle - a previously opened serverHandle.
913 *
914 * IN processName - the process of interest.
915 *
916 * OUT processTypeP - upon successful completion contains the process type
917 *
918 * OUT processInfoP - upon successful completion contains the process info
919 *
920 * LOCKS
921 *
922 * No locks are obtained or released by this function
923 *
924 * RETURN CODES
925 *
926 * Returns != 0 upon successful completion.
927 *
928 */
929
930 int ADMINAPI
931 bos_ProcessInfoGet(const void *serverHandle, char *processName,
932 bos_ProcessType_p processTypeP,
933 bos_ProcessInfo_p processInfoP, afs_status_p st)
934 {
935 int rc = 0;
936 afs_status_t tst = 0;
937 bos_server_p b_handle = (bos_server_p) serverHandle;
938 char type[BOS_MAX_NAME_LEN];
939 char *ptr = type;
940 struct bozo_status status;
941 int i;
942
943 if (!isValidServerHandle(b_handle, &tst)) {
944 goto fail_bos_ProcessInfoGet;
945 }
946
947 if ((processName == NULL) || (*processName == 0)) {
948 tst = ADMBOSPROCESSNAMENULL;
949 goto fail_bos_ProcessInfoGet;
950 }
951
952 if (processTypeP == NULL) {
953 tst = ADMBOSPROCESSTYPEPNULL;
954 goto fail_bos_ProcessInfoGet;
955 }
956
957 if (processInfoP == NULL) {
958 tst = ADMBOSPROCESSINFOPNULL;
959 goto fail_bos_ProcessInfoGet;
960 }
961
962 tst = BOZO_GetInstanceInfo(b_handle->server, processName, &ptr, &status);
963
964 if (tst != 0) {
965 goto fail_bos_ProcessInfoGet;
966 }
967
968
969 for (i = 0; (processTypes[i] != NULL); i++) {
970 if (!strcmp(processTypes[i], type)) {
971 *processTypeP = (bos_ProcessType_t) i;
972 break;
973 }
974 }
975
976 if (processTypes[i] == NULL) {
977 tst = ADMBOSINVALIDPROCESSTYPE;
978 goto fail_bos_ProcessInfoGet;
979 }
980
981 processInfoP->processGoal = (bos_ProcessExecutionState_t) status.goal;
982 processInfoP->processStartTime = status.procStartTime;
983 processInfoP->numberProcessStarts = status.procStarts;
984 processInfoP->processExitTime = status.lastAnyExit;
985 processInfoP->processExitErrorTime = status.lastErrorExit;
986 processInfoP->processErrorCode = status.errorCode;
987 processInfoP->processErrorSignal = status.errorSignal;
988 processInfoP->state = BOS_PROCESS_OK;
989
990 if (status.flags & BOZO_ERRORSTOP) {
991 processInfoP->state |= BOS_PROCESS_TOO_MANY_ERRORS;
992 }
993 if (status.flags & BOZO_HASCORE) {
994 processInfoP->state |= BOS_PROCESS_CORE_DUMPED;
995 }
996 if (status.flags & BOZO_BADDIRACCESS) {
997 processInfoP->state |= BOS_PROCESS_BAD_FILE_ACCESS;
998 }
999 rc = 1;
1000
1001 fail_bos_ProcessInfoGet:
1002
1003 if (st != NULL) {
1004 *st = tst;
1005 }
1006 return rc;
1007 }
1008
1009 /*
1010 * The iterator functions and data for the parameter retrieval functions
1011 */
1012
1013 typedef struct param_get {
1014 int next;
1015 struct rx_connection *server;
1016 char processName[BOS_MAX_NAME_LEN];
1017 char param[CACHED_ITEMS][BOS_MAX_NAME_LEN];
1018 } param_get_t, *param_get_p;
1019
1020 static int
1021 GetParameterRPC(void *rpc_specific, int slot, int *last_item,
1022 int *last_item_contains_data, afs_status_p st)
1023 {
1024 int rc = 0;
1025 afs_status_t tst = 0;
1026 param_get_p param = (param_get_p) rpc_specific;
1027 char *ptr = (char *)&param->param[slot];
1028
1029 tst =
1030 BOZO_GetInstanceParm(param->server, param->processName, param->next++,
1031 &ptr);
1032
1033 if (tst == 0) {
1034 rc = 1;
1035 } else if (tst == BZDOM) {
1036 tst = 0;
1037 rc = 1;
1038 *last_item = 1;
1039 *last_item_contains_data = 0;
1040 }
1041
1042 if (st != NULL) {
1043 *st = tst;
1044 }
1045 return rc;
1046 }
1047
1048 static int
1049 GetParameterFromCache(void *rpc_specific, int slot, void *dest,
1050 afs_status_p st)
1051 {
1052 int rc = 0;
1053 afs_status_t tst = 0;
1054 param_get_p param = (param_get_p) rpc_specific;
1055
1056 strcpy((char *)dest, (char *)&param->param[slot]);
1057 rc = 1;
1058
1059 if (st != NULL) {
1060 *st = tst;
1061 }
1062 return rc;
1063 }
1064
1065 /*
1066 * bos_ProcessParameterGetBegin - begin iterating over the parameters
1067 * of a particular process.
1068 *
1069 * PARAMETERS
1070 *
1071 * IN serverHandle - a previously opened serverHandle.
1072 *
1073 * IN processName - the process whose parameters are returned.
1074 *
1075 * OUT iter - an iterator that can be passed to bos_ProcessParameterGetNext
1076 * to retrieve the parameters.
1077 *
1078 * LOCKS
1079 *
1080 * No locks are obtained or released by this function
1081 *
1082 * RETURN CODES
1083 *
1084 * Returns != 0 upon successful completion.
1085 *
1086 */
1087
1088 int ADMINAPI
1089 bos_ProcessParameterGetBegin(const void *serverHandle,
1090 const char *processName, void **iterationIdP,
1091 afs_status_p st)
1092 {
1093 int rc = 0;
1094 afs_status_t tst = 0;
1095 bos_server_p b_handle = (bos_server_p) serverHandle;
1096 afs_admin_iterator_p iter = malloc(sizeof(afs_admin_iterator_t));
1097 param_get_p param = malloc(sizeof(param_get_t));
1098
1099 if (!isValidServerHandle(b_handle, &tst)) {
1100 goto fail_bos_ProcessParameterGetBegin;
1101 }
1102
1103 if ((processName == NULL) || (*processName == 0)) {
1104 tst = ADMBOSPROCESSNAMENULL;
1105 goto fail_bos_ProcessParameterGetBegin;
1106 }
1107
1108 if (iterationIdP == NULL) {
1109 tst = ADMITERATIONIDPNULL;
1110 goto fail_bos_ProcessParameterGetBegin;
1111 }
1112
1113 if ((iter == NULL) || (param == NULL)) {
1114 tst = ADMNOMEM;
1115 goto fail_bos_ProcessParameterGetBegin;
1116 }
1117
1118 param->next = 0;
1119 param->server = b_handle->server;
1120 strcpy(param->processName, processName);
1121
1122 if (IteratorInit
1123 (iter, (void *)param, GetParameterRPC, GetParameterFromCache, NULL,
1124 NULL, &tst)) {
1125 *iterationIdP = (void *)iter;
1126 } else {
1127 goto fail_bos_ProcessParameterGetBegin;
1128 }
1129 rc = 1;
1130
1131 fail_bos_ProcessParameterGetBegin:
1132
1133 if (rc == 0) {
1134 if (iter != NULL) {
1135 free(iter);
1136 }
1137 if (param != NULL) {
1138 free(param);
1139 }
1140 }
1141
1142 if (st != NULL) {
1143 *st = tst;
1144 }
1145 return rc;
1146 }
1147
1148 /*
1149 * bos_ProcessParameterGetNext - retrieve the next parameter
1150 * from the bos server.
1151 *
1152 * PARAMETERS
1153 *
1154 * IN iterationId - an iterator previously returned by
1155 * bos_ProcessParameterGetBegin
1156 *
1157 * OUT parameter - upon successful completion contains the next parameter
1158 * retrieved from the server.
1159 *
1160 * LOCKS
1161 *
1162 * No locks are obtained or released by this function
1163 *
1164 * RETURN CODES
1165 *
1166 * Returns != 0 upon successful completion.
1167 *
1168 */
1169
1170 int ADMINAPI
1171 bos_ProcessParameterGetNext(const void *iterationId, char *parameter,
1172 afs_status_p st)
1173 {
1174 int rc = 0;
1175 afs_status_t tst = 0;
1176 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1177
1178 if (iterationId == NULL) {
1179 tst = ADMITERATIONIDPNULL;
1180 goto fail_bos_ProcessParameterGetNext;
1181 }
1182
1183 if (parameter == NULL) {
1184 tst = ADMBOSPARAMETERNULL;
1185 goto fail_bos_ProcessParameterGetNext;
1186 }
1187
1188 rc = IteratorNext(iter, (void *)parameter, &tst);
1189
1190 fail_bos_ProcessParameterGetNext:
1191
1192 if (st != NULL) {
1193 *st = tst;
1194 }
1195 return rc;
1196 }
1197
1198 /*
1199 * bos_ProcessParameterGetDone - finish using a process name iterator.
1200 *
1201 * PARAMETERS
1202 *
1203 * IN iterationId - an iterator previously returned by
1204 * bos_ProcessParameterGetBegin
1205 *
1206 * LOCKS
1207 *
1208 * No locks are obtained or released by this function
1209 *
1210 * RETURN CODES
1211 *
1212 * Returns != 0 upon successful completion.
1213 *
1214 */
1215
1216 int ADMINAPI
1217 bos_ProcessParameterGetDone(const void *iterationId, afs_status_p st)
1218 {
1219 int rc = 0;
1220 afs_status_t tst = 0;
1221 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1222
1223 if (iterationId == NULL) {
1224 tst = ADMITERATIONIDPNULL;
1225 goto fail_bos_ProcessParameterGetDone;
1226 }
1227
1228 rc = IteratorDone(iter, &tst);
1229
1230 fail_bos_ProcessParameterGetDone:
1231
1232 if (st != NULL) {
1233 *st = tst;
1234 }
1235 return rc;
1236 }
1237
1238 /*
1239 * bos_ProcessNotifierGet - retrieve the notifier associated with a
1240 * process.
1241 *
1242 * PARAMETERS
1243 *
1244 * IN serverHandle - a previously opened serverHandle.
1245 *
1246 * IN processName - the process whose notifier we are retrieving.
1247 *
1248 * OUT notifier - upon successful completion contains the notifier.
1249 *
1250 * LOCKS
1251 *
1252 * No locks are obtained or released by this function
1253 *
1254 * RETURN CODES
1255 *
1256 * Returns != 0 upon successful completion.
1257 *
1258 */
1259
1260 int ADMINAPI
1261 bos_ProcessNotifierGet(const void *serverHandle, const char *processName,
1262 char *notifier, afs_status_p st)
1263 {
1264 int rc = 0;
1265 afs_status_t tst = 0;
1266 bos_server_p b_handle = (bos_server_p) serverHandle;
1267
1268 if (!isValidServerHandle(b_handle, &tst)) {
1269 goto fail_bos_ProcessNotifierGet;
1270 }
1271
1272 if ((processName == NULL) || (*processName == 0)) {
1273 tst = ADMBOSPROCESSNAMENULL;
1274 goto fail_bos_ProcessNotifierGet;
1275 }
1276
1277 if (notifier == NULL) {
1278 tst = ADMBOSNOTIFIERNULL;
1279 goto fail_bos_ProcessNotifierGet;
1280 }
1281
1282 tst = BOZO_GetInstanceParm(b_handle->server, (char *)processName,
1283 999, &notifier);
1284
1285 if (tst == 0) {
1286 rc = 1;
1287 }
1288
1289 fail_bos_ProcessNotifierGet:
1290
1291 if (st != NULL) {
1292 *st = tst;
1293 }
1294 return rc;
1295 }
1296
1297 /*
1298 * bos_ProcessRestart - restart a particular process.
1299 *
1300 * PARAMETERS
1301 *
1302 * IN serverHandle - a previously opened serverHandle.
1303 *
1304 * IN processName - the process to restart
1305 *
1306 * LOCKS
1307 *
1308 * No locks are obtained or released by this function
1309 *
1310 * RETURN CODES
1311 *
1312 * Returns != 0 upon successful completion.
1313 *
1314 */
1315
1316 int ADMINAPI
1317 bos_ProcessRestart(const void *serverHandle, const char *processName,
1318 afs_status_p st)
1319 {
1320 int rc = 0;
1321 afs_status_t tst = 0;
1322 bos_server_p b_handle = (bos_server_p) serverHandle;
1323
1324 if (!isValidServerHandle(b_handle, &tst)) {
1325 goto fail_bos_ProcessRestart;
1326 }
1327
1328 if ((processName == NULL) || (*processName == 0)) {
1329 tst = ADMBOSPROCESSNAMENULL;
1330 goto fail_bos_ProcessRestart;
1331 }
1332
1333 tst = BOZO_Restart(b_handle->server, (char *)processName);
1334
1335 if (tst == 0) {
1336 rc = 1;
1337 }
1338
1339 fail_bos_ProcessRestart:
1340
1341 if (st != NULL) {
1342 *st = tst;
1343 }
1344 return rc;
1345 }
1346
1347 /*
1348 * bos_ProcessAllStop - stop all running processes at a server.
1349 *
1350 * PARAMETERS
1351 *
1352 * IN serverHandle - a previously opened serverHandle.
1353 *
1354 * LOCKS
1355 *
1356 * No locks are obtained or released by this function
1357 *
1358 * RETURN CODES
1359 *
1360 * Returns != 0 upon successful completion.
1361 *
1362 */
1363
1364 int ADMINAPI
1365 bos_ProcessAllStop(const void *serverHandle, afs_status_p st)
1366 {
1367 int rc = 0;
1368 afs_status_t tst = 0;
1369 bos_server_p b_handle = (bos_server_p) serverHandle;
1370
1371 if (!isValidServerHandle(b_handle, &tst)) {
1372 goto fail_bos_ProcessAllStop;
1373 }
1374
1375 tst = BOZO_ShutdownAll(b_handle->server);
1376
1377 if (tst == 0) {
1378 rc = 1;
1379 }
1380
1381 fail_bos_ProcessAllStop:
1382
1383 if (st != NULL) {
1384 *st = tst;
1385 }
1386 return rc;
1387 }
1388
1389 /*
1390 * bos_ProcessAllStart - start all processes that should be running at a
1391 * server.
1392 *
1393 * PARAMETERS
1394 *
1395 * IN serverHandle - a previously opened serverHandle.
1396 *
1397 * LOCKS
1398 *
1399 * No locks are obtained or released by this function
1400 *
1401 * RETURN CODES
1402 *
1403 * Returns != 0 upon successful completion.
1404 *
1405 */
1406
1407 int ADMINAPI
1408 bos_ProcessAllStart(const void *serverHandle, afs_status_p st)
1409 {
1410 int rc = 0;
1411 afs_status_t tst = 0;
1412 bos_server_p b_handle = (bos_server_p) serverHandle;
1413
1414 if (!isValidServerHandle(b_handle, &tst)) {
1415 goto fail_bos_ProcessAllStart;
1416 }
1417
1418 tst = BOZO_StartupAll(b_handle->server);
1419
1420 if (tst == 0) {
1421 rc = 1;
1422 }
1423
1424 fail_bos_ProcessAllStart:
1425
1426 if (st != NULL) {
1427 *st = tst;
1428 }
1429 return rc;
1430 }
1431
1432 /*
1433 * bos_ProcessAllWaitStop - stop all processes, and block until they have
1434 * exited.
1435 *
1436 * PARAMETERS
1437 *
1438 * IN serverHandle - a previously opened serverHandle.
1439 *
1440 * LOCKS
1441 *
1442 * No locks are obtained or released by this function
1443 *
1444 * RETURN CODES
1445 *
1446 * Returns != 0 upon successful completion.
1447 *
1448 */
1449
1450 int ADMINAPI
1451 bos_ProcessAllWaitStop(const void *serverHandle, afs_status_p st)
1452 {
1453 int rc = 0;
1454 afs_status_t tst = 0;
1455 bos_server_p b_handle = (bos_server_p) serverHandle;
1456
1457 if (!isValidServerHandle(b_handle, &tst)) {
1458 goto fail_bos_ProcessAllWaitStop;
1459 }
1460
1461 if (!bos_ProcessAllStop(serverHandle, &tst)) {
1462 goto fail_bos_ProcessAllWaitStop;
1463 }
1464
1465 tst = BOZO_WaitAll(b_handle->server);
1466
1467 if (tst == 0) {
1468 rc = 1;
1469 }
1470
1471 fail_bos_ProcessAllWaitStop:
1472
1473 if (st != NULL) {
1474 *st = tst;
1475 }
1476 return rc;
1477 }
1478
1479 /*
1480 * bos_ProcessAllWaitTransition - block until all processes at the bosserver
1481 * have reached their desired state.
1482 *
1483 * PARAMETERS
1484 *
1485 * IN serverHandle - a previously opened serverHandle.
1486 *
1487 * LOCKS
1488 *
1489 * No locks are obtained or released by this function
1490 *
1491 * RETURN CODES
1492 *
1493 * Returns != 0 upon successful completion.
1494 *
1495 */
1496
1497 int ADMINAPI
1498 bos_ProcessAllWaitTransition(const void *serverHandle, afs_status_p st)
1499 {
1500 int rc = 0;
1501 afs_status_t tst = 0;
1502 bos_server_p b_handle = (bos_server_p) serverHandle;
1503
1504 if (!isValidServerHandle(b_handle, &tst)) {
1505 goto fail_bos_ProcessAllWaitTransition;
1506 }
1507
1508 tst = BOZO_WaitAll(b_handle->server);
1509
1510 if (tst == 0) {
1511 rc = 1;
1512 }
1513
1514 fail_bos_ProcessAllWaitTransition:
1515
1516 if (st != NULL) {
1517 *st = tst;
1518 }
1519 return rc;
1520 }
1521
1522 /*
1523 * bos_ProcessAllStopAndRestart - stop all the running processes, restart
1524 * them, and optionally restart the bosserver itself.
1525 * exited.
1526 *
1527 * PARAMETERS
1528 *
1529 * IN serverHandle - a previously opened serverHandle.
1530 *
1531 * IN restartBosServer - flag to indicate whether to restart bosserver.
1532 *
1533 * LOCKS
1534 *
1535 * No locks are obtained or released by this function
1536 *
1537 * RETURN CODES
1538 *
1539 * Returns != 0 upon successful completion.
1540 *
1541 */
1542
1543 int ADMINAPI
1544 bos_ProcessAllStopAndRestart(const void *serverHandle,
1545 bos_RestartBosServer_t restartBosServer,
1546 afs_status_p st)
1547 {
1548 int rc = 0;
1549 afs_status_t tst = 0;
1550 bos_server_p b_handle = (bos_server_p) serverHandle;
1551
1552 if (!isValidServerHandle(b_handle, &tst)) {
1553 goto fail_bos_ProcessAllStopAndRestart;
1554 }
1555
1556 if (restartBosServer == BOS_RESTART_BOS_SERVER) {
1557 tst = BOZO_ReBozo(b_handle->server);
1558 if (tst != 0) {
1559 goto fail_bos_ProcessAllStopAndRestart;
1560 }
1561 }
1562
1563 tst = BOZO_RestartAll(b_handle->server);
1564
1565 if (tst == 0) {
1566 rc = 1;
1567 }
1568
1569 fail_bos_ProcessAllStopAndRestart:
1570
1571 if (st != NULL) {
1572 *st = tst;
1573 }
1574 return rc;
1575 }
1576
1577 /*
1578 * bos_AdminCreate - create a new admin.
1579 *
1580 * PARAMETERS
1581 *
1582 * IN serverHandle - a previously opened serverHandle.
1583 *
1584 * IN adminName - the new admin name.
1585 *
1586 * LOCKS
1587 *
1588 * No locks are obtained or released by this function
1589 *
1590 * RETURN CODES
1591 *
1592 * Returns != 0 upon successful completion.
1593 *
1594 */
1595
1596 int ADMINAPI
1597 bos_AdminCreate(const void *serverHandle, const char *adminName,
1598 afs_status_p st)
1599 {
1600 int rc = 0;
1601 afs_status_t tst = 0;
1602 bos_server_p b_handle = (bos_server_p) serverHandle;
1603
1604 if (!isValidServerHandle(b_handle, &tst)) {
1605 goto fail_bos_AdminCreate;
1606 }
1607
1608 if ((adminName == NULL) || (*adminName == 0)) {
1609 tst = ADMBOSADMINNAMENULL;
1610 goto fail_bos_AdminCreate;
1611 }
1612
1613 tst = BOZO_AddSUser(b_handle->server, (char *)adminName);
1614
1615 if (tst == 0) {
1616 rc = 1;
1617 }
1618
1619 fail_bos_AdminCreate:
1620
1621 if (st != NULL) {
1622 *st = tst;
1623 }
1624 return rc;
1625 }
1626
1627 /*
1628 * bos_AdminDelete - delete a new admin.
1629 *
1630 * PARAMETERS
1631 *
1632 * IN serverHandle - a previously opened serverHandle.
1633 *
1634 * IN adminName - the admin name.
1635 *
1636 * LOCKS
1637 *
1638 * No locks are obtained or released by this function
1639 *
1640 * RETURN CODES
1641 *
1642 * Returns != 0 upon successful completion.
1643 *
1644 */
1645
1646 int ADMINAPI
1647 bos_AdminDelete(const void *serverHandle, const char *adminName,
1648 afs_status_p st)
1649 {
1650 int rc = 0;
1651 afs_status_t tst = 0;
1652 bos_server_p b_handle = (bos_server_p) serverHandle;
1653
1654 if (!isValidServerHandle(b_handle, &tst)) {
1655 goto fail_bos_AdminDelete;
1656 }
1657
1658 if ((adminName == NULL) || (*adminName == 0)) {
1659 tst = ADMBOSADMINNAMENULL;
1660 goto fail_bos_AdminDelete;
1661 }
1662
1663 tst = BOZO_DeleteSUser(b_handle->server, (char *)adminName);
1664
1665 if (tst == 0) {
1666 rc = 1;
1667 }
1668
1669 fail_bos_AdminDelete:
1670
1671 if (st != NULL) {
1672 *st = tst;
1673 }
1674 return rc;
1675 }
1676
1677 /*
1678 * The iterator functions and data for the admin retrieval functions
1679 */
1680
1681 typedef struct admin_get {
1682 int next;
1683 struct rx_connection *server;
1684 char admin[CACHED_ITEMS][BOS_MAX_NAME_LEN];
1685 } admin_get_t, *admin_get_p;
1686
1687 static int
1688 GetAdminRPC(void *rpc_specific, int slot, int *last_item,
1689 int *last_item_contains_data, afs_status_p st)
1690 {
1691 int rc = 0;
1692 afs_status_t tst = 0;
1693 admin_get_p admin = (admin_get_p) rpc_specific;
1694 char *ptr = (char *)&admin->admin[slot];
1695
1696 tst = BOZO_ListSUsers(admin->server, admin->next++, &ptr);
1697
1698 /*
1699 * There's no way to tell the difference between an rpc failure
1700 * and the end of the list, so we assume that any error means the
1701 * end of the list
1702 */
1703
1704 if (tst != 0) {
1705 tst = 0;
1706 *last_item = 1;
1707 *last_item_contains_data = 0;
1708 }
1709 rc = 1;
1710
1711 if (st != NULL) {
1712 *st = tst;
1713 }
1714 return rc;
1715 }
1716
1717 static int
1718 GetAdminFromCache(void *rpc_specific, int slot, void *dest, afs_status_p st)
1719 {
1720 int rc = 0;
1721 afs_status_t tst = 0;
1722 admin_get_p admin = (admin_get_p) rpc_specific;
1723
1724 strcpy((char *)dest, (char *)&admin->admin[slot]);
1725 rc = 1;
1726
1727 if (st != NULL) {
1728 *st = tst;
1729 }
1730 return rc;
1731 }
1732
1733 /*
1734 * bos_AdminGetBegin - begin iterating over the administrators.
1735 *
1736 * PARAMETERS
1737 *
1738 * IN serverHandle - a previously opened serverHandle.
1739 *
1740 * OUT iter - an iterator that can be passed to bos_AdminGetBegin
1741 * to retrieve the administrators.
1742 *
1743 * LOCKS
1744 *
1745 * No locks are obtained or released by this function
1746 *
1747 * RETURN CODES
1748 *
1749 * Returns != 0 upon successful completion.
1750 *
1751 */
1752
1753 int ADMINAPI
1754 bos_AdminGetBegin(const void *serverHandle, void **iterationIdP,
1755 afs_status_p st)
1756 {
1757 int rc = 0;
1758 afs_status_t tst = 0;
1759 bos_server_p b_handle = (bos_server_p) serverHandle;
1760 afs_admin_iterator_p iter = malloc(sizeof(afs_admin_iterator_t));
1761 admin_get_p admin = malloc(sizeof(admin_get_t));
1762
1763 if (!isValidServerHandle(b_handle, &tst)) {
1764 goto fail_bos_AdminGetBegin;
1765 }
1766
1767 if (iterationIdP == NULL) {
1768 tst = ADMITERATIONIDPNULL;
1769 goto fail_bos_AdminGetBegin;
1770 }
1771
1772 if ((iter == NULL) || (admin == NULL)) {
1773 tst = ADMNOMEM;
1774 goto fail_bos_AdminGetBegin;
1775 }
1776
1777 admin->next = 0;
1778 admin->server = b_handle->server;
1779
1780 if (IteratorInit
1781 (iter, (void *)admin, GetAdminRPC, GetAdminFromCache, NULL, NULL,
1782 &tst)) {
1783 *iterationIdP = (void *)iter;
1784 rc = 1;
1785 }
1786
1787 fail_bos_AdminGetBegin:
1788
1789 if (rc == 0) {
1790 if (iter != NULL) {
1791 free(iter);
1792 }
1793 if (admin != NULL) {
1794 free(admin);
1795 }
1796 }
1797
1798 if (st != NULL) {
1799 *st = tst;
1800 }
1801 return rc;
1802 }
1803
1804 /*
1805 * bos_AdminGetNext - retrieve the next administrator
1806 * from the bos server.
1807 *
1808 * PARAMETERS
1809 *
1810 * IN iterationId - an iterator previously returned by
1811 * bos_AdminGetBegin
1812 *
1813 * OUT adminName - upon successful completion contains the next administrator
1814 * retrieved from the server.
1815 *
1816 * LOCKS
1817 *
1818 * No locks are obtained or released by this function
1819 *
1820 * RETURN CODES
1821 *
1822 * Returns != 0 upon successful completion.
1823 *
1824 */
1825
1826 int ADMINAPI
1827 bos_AdminGetNext(const void *iterationId, char *adminName, afs_status_p st)
1828 {
1829 int rc = 0;
1830 afs_status_t tst = 0;
1831 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1832
1833 if (iterationId == NULL) {
1834 tst = ADMITERATIONIDPNULL;
1835 goto fail_bos_AdminGetNext;
1836 }
1837
1838 if (adminName == NULL) {
1839 tst = ADMBOSADMINNAMENULL;
1840 goto fail_bos_AdminGetNext;
1841 }
1842
1843 rc = IteratorNext(iter, (void *)adminName, &tst);
1844
1845 fail_bos_AdminGetNext:
1846
1847 if (st != NULL) {
1848 *st = tst;
1849 }
1850 return rc;
1851 }
1852
1853 /*
1854 * bos_AdminGetDone - finish using a administrator iterator.
1855 *
1856 * PARAMETERS
1857 *
1858 * IN iterationId - an iterator previously returned by
1859 * bos_AdminGetBegin
1860 *
1861 * LOCKS
1862 *
1863 * No locks are obtained or released by this function
1864 *
1865 * RETURN CODES
1866 *
1867 * Returns != 0 upon successful completion.
1868 *
1869 */
1870
1871 int ADMINAPI
1872 bos_AdminGetDone(const void *iterationId, afs_status_p st)
1873 {
1874 int rc = 0;
1875 afs_status_t tst = 0;
1876 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1877
1878 if (iterationId == NULL) {
1879 tst = ADMITERATIONIDPNULL;
1880 goto fail_bos_AdminGetDone;
1881 }
1882
1883 rc = IteratorDone(iter, &tst);
1884
1885 fail_bos_AdminGetDone:
1886
1887 if (st != NULL) {
1888 *st = tst;
1889 }
1890 return rc;
1891 }
1892
1893 /*
1894 * bos_KeyCreate - add a new key to the keyfile.
1895 *
1896 * PARAMETERS
1897 *
1898 * IN serverHandle - a previously opened serverHandle.
1899 *
1900 * IN keyVersionNumber - the key version number.
1901 *
1902 * IN key - the new key.
1903 *
1904 * LOCKS
1905 *
1906 * No locks are obtained or released by this function
1907 *
1908 * RETURN CODES
1909 *
1910 * Returns != 0 upon successful completion.
1911 *
1912 */
1913
1914 int ADMINAPI
1915 bos_KeyCreate(const void *serverHandle, int keyVersionNumber,
1916 const kas_encryptionKey_p key, afs_status_p st)
1917 {
1918 int rc = 0;
1919 afs_status_t tst = 0;
1920 bos_server_p b_handle = (bos_server_p) serverHandle;
1921
1922 if (!isValidServerHandle(b_handle, &tst)) {
1923 goto fail_bos_KeyCreate;
1924 }
1925
1926 if (key == NULL) {
1927 tst = ADMBOSKEYNULL;
1928 goto fail_bos_KeyCreate;
1929 }
1930
1931 tst = BOZO_AddKey(b_handle->server_encrypt, keyVersionNumber, kas_to_bozoptr(key));
1932
1933 if (tst == 0) {
1934 rc = 1;
1935 }
1936
1937 fail_bos_KeyCreate:
1938
1939 if (st != NULL) {
1940 *st = tst;
1941 }
1942 return rc;
1943 }
1944
1945 /*
1946 * bos_KeyDelete - delete an existing key from the keyfile.
1947 *
1948 * PARAMETERS
1949 *
1950 * IN serverHandle - a previously opened serverHandle.
1951 *
1952 * IN keyVersionNumber - the key version number.
1953 *
1954 * LOCKS
1955 *
1956 * No locks are obtained or released by this function
1957 *
1958 * RETURN CODES
1959 *
1960 * Returns != 0 upon successful completion.
1961 *
1962 */
1963
1964 int ADMINAPI
1965 bos_KeyDelete(const void *serverHandle, int keyVersionNumber, afs_status_p st)
1966 {
1967 int rc = 0;
1968 afs_status_t tst = 0;
1969 bos_server_p b_handle = (bos_server_p) serverHandle;
1970
1971 if (!isValidServerHandle(b_handle, &tst)) {
1972 goto fail_bos_KeyDelete;
1973 }
1974
1975 tst = BOZO_DeleteKey(b_handle->server, keyVersionNumber);
1976
1977 if (tst == 0) {
1978 rc = 1;
1979 }
1980
1981 fail_bos_KeyDelete:
1982
1983 if (st != NULL) {
1984 *st = tst;
1985 }
1986 return rc;
1987 }
1988
1989 /*
1990 * The iterator functions and data for the key retrieval functions
1991 */
1992
1993 typedef struct key_get {
1994 int next;
1995 struct rx_connection *server;
1996 bos_KeyInfo_t key[CACHED_ITEMS];
1997 } key_get_t, *key_get_p;
1998
1999 static int
2000 GetKeyRPC(void *rpc_specific, int slot, int *last_item,
2001 int *last_item_contains_data, afs_status_p st)
2002 {
2003 int rc = 0;
2004 afs_status_t tst = 0;
2005 key_get_p key = (key_get_p) rpc_specific;
2006 struct bozo_keyInfo keyInfo;
2007
2008 tst =
2009 BOZO_ListKeys(key->server, key->next++,
2010 &key->key[slot].keyVersionNumber, kas_to_bozoptr(&key->key[slot].key),
2011 &keyInfo);
2012
2013
2014 if (tst == 0) {
2015 key->key[slot].keyStatus.lastModificationDate = keyInfo.mod_sec;
2016 key->key[slot].keyStatus.lastModificationMicroSeconds =
2017 keyInfo.mod_usec;
2018 key->key[slot].keyStatus.checkSum = keyInfo.keyCheckSum;
2019 rc = 1;
2020 } else if (tst == BZDOM) {
2021 tst = 0;
2022 rc = 1;
2023 *last_item = 1;
2024 *last_item_contains_data = 0;
2025 }
2026
2027 if (st != NULL) {
2028 *st = tst;
2029 }
2030 return rc;
2031 }
2032
2033 static int
2034 GetKeyFromCache(void *rpc_specific, int slot, void *dest, afs_status_p st)
2035 {
2036 int rc = 0;
2037 afs_status_t tst = 0;
2038 key_get_p key = (key_get_p) rpc_specific;
2039
2040 memcpy(dest, &key->key[slot], sizeof(bos_KeyInfo_t));
2041 rc = 1;
2042
2043 if (st != NULL) {
2044 *st = tst;
2045 }
2046 return rc;
2047 }
2048
2049 /*
2050 * bos_KeyGetBegin - begin iterating over the keys.
2051 *
2052 * PARAMETERS
2053 *
2054 * IN serverHandle - a previously opened serverHandle.
2055 *
2056 * OUT iter - an iterator that can be passed to bos_KeyGetNext
2057 * to retrieve the keys.
2058 *
2059 * LOCKS
2060 *
2061 * No locks are obtained or released by this function
2062 *
2063 * RETURN CODES
2064 *
2065 * Returns != 0 upon successful completion.
2066 *
2067 */
2068
2069 int ADMINAPI
2070 bos_KeyGetBegin(const void *serverHandle, void **iterationIdP,
2071 afs_status_p st)
2072 {
2073 int rc = 0;
2074 afs_status_t tst = 0;
2075 bos_server_p b_handle = (bos_server_p) serverHandle;
2076 afs_admin_iterator_p iter = malloc(sizeof(afs_admin_iterator_t));
2077 key_get_p key = malloc(sizeof(key_get_t));
2078
2079 if (!isValidServerHandle(b_handle, &tst)) {
2080 goto fail_bos_KeyGetBegin;
2081 }
2082
2083 if (iterationIdP == NULL) {
2084 tst = ADMITERATIONIDPNULL;
2085 goto fail_bos_KeyGetBegin;
2086 }
2087
2088 if ((iter == NULL) || (key == NULL)) {
2089 tst = ADMNOMEM;
2090 goto fail_bos_KeyGetBegin;
2091 }
2092
2093 key->next = 0;
2094 key->server = b_handle->server_encrypt;
2095
2096 if (IteratorInit
2097 (iter, (void *)key, GetKeyRPC, GetKeyFromCache, NULL, NULL, &tst)) {
2098 *iterationIdP = (void *)iter;
2099 rc = 1;
2100 }
2101
2102 fail_bos_KeyGetBegin:
2103
2104 if (rc == 0) {
2105 if (iter != NULL) {
2106 free(iter);
2107 }
2108 if (key != NULL) {
2109 free(key);
2110 }
2111 }
2112
2113 if (st != NULL) {
2114 *st = tst;
2115 }
2116 return rc;
2117 }
2118
2119 /*
2120 * bos_KeyGetNext - retrieve the next key
2121 * from the bos server.
2122 *
2123 * PARAMETERS
2124 *
2125 * IN iterationId - an iterator previously returned by
2126 * bos_KeyGetBegin
2127 *
2128 * OUT keyP - upon successful completion contains the next key
2129 * retrieved from the server.
2130 *
2131 * LOCKS
2132 *
2133 * No locks are obtained or released by this function
2134 *
2135 * RETURN CODES
2136 *
2137 * Returns != 0 upon successful completion.
2138 *
2139 */
2140
2141 int ADMINAPI
2142 bos_KeyGetNext(const void *iterationId, bos_KeyInfo_p keyP, afs_status_p st)
2143 {
2144 int rc = 0;
2145 afs_status_t tst = 0;
2146 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
2147
2148 if (iterationId == NULL) {
2149 tst = ADMITERATIONIDPNULL;
2150 goto fail_bos_KeyGetNext;
2151 }
2152
2153 if (keyP == NULL) {
2154 tst = ADMBOSKEYPNULL;
2155 goto fail_bos_KeyGetNext;
2156 }
2157
2158 rc = IteratorNext(iter, (void *)keyP, &tst);
2159
2160 fail_bos_KeyGetNext:
2161
2162 if (st != NULL) {
2163 *st = tst;
2164 }
2165 return rc;
2166 }
2167
2168 /*
2169 * bos_KeyGetDone - finish using a key iterator.
2170 *
2171 * PARAMETERS
2172 *
2173 * IN iterationId - an iterator previously returned by
2174 * bos_KeyGetBegin
2175 *
2176 * LOCKS
2177 *
2178 * No locks are obtained or released by this function
2179 *
2180 * RETURN CODES
2181 *
2182 * Returns != 0 upon successful completion.
2183 *
2184 */
2185
2186 int ADMINAPI
2187 bos_KeyGetDone(const void *iterationId, afs_status_p st)
2188 {
2189 int rc = 0;
2190 afs_status_t tst = 0;
2191 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
2192
2193 if (iterationId == NULL) {
2194 tst = ADMITERATIONIDPNULL;
2195 goto fail_bos_KeyGetDone;
2196 }
2197
2198 rc = IteratorDone(iter, &tst);
2199
2200 fail_bos_KeyGetDone:
2201
2202 if (st != NULL) {
2203 *st = tst;
2204 }
2205 return rc;
2206 }
2207
2208 /*
2209 * bos_CellSet - set the cell name at a bos server.
2210 *
2211 * PARAMETERS
2212 *
2213 * IN serverHandle - a previously opened serverHandle.
2214 *
2215 * IN cellName - the new cell name.
2216 *
2217 * LOCKS
2218 *
2219 * No locks are obtained or released by this function
2220 *
2221 * RETURN CODES
2222 *
2223 * Returns != 0 upon successful completion.
2224 */
2225
2226 int ADMINAPI
2227 bos_CellSet(const void *serverHandle, const char *cellName, afs_status_p st)
2228 {
2229 int rc = 0;
2230 afs_status_t tst = 0;
2231 bos_server_p b_handle = (bos_server_p) serverHandle;
2232
2233 if (!isValidServerHandle(b_handle, &tst)) {
2234 goto fail_bos_CellSet;
2235 }
2236
2237 if ((cellName == NULL) || (*cellName == 0)) {
2238 tst = ADMCLIENTCELLNAMENULL;
2239 goto fail_bos_CellSet;
2240 }
2241
2242 tst = BOZO_SetCellName(b_handle->server, (char *)cellName);
2243
2244 if (tst == 0) {
2245 rc = 1;
2246 }
2247
2248 fail_bos_CellSet:
2249
2250 if (st != NULL) {
2251 *st = tst;
2252 }
2253 return rc;
2254 }
2255
2256 /*
2257 * bos_CellGet - get the cell name at a bos server.
2258 *
2259 * PARAMETERS
2260 *
2261 * IN serverHandle - a previously opened serverHandle.
2262 *
2263 * OUT cellName - the cell name.
2264 *
2265 * LOCKS
2266 *
2267 * No locks are obtained or released by this function
2268 *
2269 * RETURN CODES
2270 *
2271 * Returns != 0 upon successful completion.
2272 */
2273
2274 int ADMINAPI
2275 bos_CellGet(const void *serverHandle, char *cellName, afs_status_p st)
2276 {
2277 int rc = 0;
2278 afs_status_t tst = 0;
2279 bos_server_p b_handle = (bos_server_p) serverHandle;
2280
2281 if (!isValidServerHandle(b_handle, &tst)) {
2282 goto fail_bos_CellGet;
2283 }
2284
2285 if (cellName == NULL) {
2286 tst = ADMCLIENTCELLNAMENULL;
2287 goto fail_bos_CellGet;
2288 }
2289
2290 tst = BOZO_GetCellName(b_handle->server, &cellName);
2291
2292 if (tst == 0) {
2293 rc = 1;
2294 }
2295
2296 fail_bos_CellGet:
2297
2298 if (st != NULL) {
2299 *st = tst;
2300 }
2301 return rc;
2302 }
2303
2304 /*
2305 * bos_HostCreate - add a new host to the cell.
2306 *
2307 * PARAMETERS
2308 *
2309 * IN serverHandle - a previously opened serverHandle.
2310 *
2311 * IN hostName - the new host.
2312 *
2313 * LOCKS
2314 *
2315 * No locks are obtained or released by this function
2316 *
2317 * RETURN CODES
2318 *
2319 * Returns != 0 upon successful completion.
2320 */
2321
2322 int ADMINAPI
2323 bos_HostCreate(const void *serverHandle, const char *hostName,
2324 afs_status_p st)
2325 {
2326 int rc = 0;
2327 afs_status_t tst = 0;
2328 bos_server_p b_handle = (bos_server_p) serverHandle;
2329
2330 if (!isValidServerHandle(b_handle, &tst)) {
2331 goto fail_bos_HostCreate;
2332 }
2333
2334 if ((hostName == NULL) || (*hostName == 0)) {
2335 tst = ADMBOSHOSTNAMENULL;
2336 goto fail_bos_HostCreate;
2337 }
2338
2339 tst = BOZO_AddCellHost(b_handle->server, (char *)hostName);
2340
2341 if (tst == 0) {
2342 rc = 1;
2343 }
2344
2345 fail_bos_HostCreate:
2346
2347 if (st != NULL) {
2348 *st = tst;
2349 }
2350 return rc;
2351 }
2352
2353 /*
2354 * bos_HostDelete - delete a host from the cell.
2355 *
2356 * PARAMETERS
2357 *
2358 * IN serverHandle - a previously opened serverHandle.
2359 *
2360 * IN hostName - the host.
2361 *
2362 * LOCKS
2363 *
2364 * No locks are obtained or released by this function
2365 *
2366 * RETURN CODES
2367 *
2368 * Returns != 0 upon successful completion.
2369 */
2370
2371 int ADMINAPI
2372 bos_HostDelete(const void *serverHandle, const char *hostName,
2373 afs_status_p st)
2374 {
2375 int rc = 0;
2376 afs_status_t tst = 0;
2377 bos_server_p b_handle = (bos_server_p) serverHandle;
2378
2379 if (!isValidServerHandle(b_handle, &tst)) {
2380 goto fail_bos_HostDelete;
2381 }
2382
2383 if ((hostName == NULL) || (*hostName == 0)) {
2384 tst = ADMBOSHOSTNAMENULL;
2385 goto fail_bos_HostDelete;
2386 }
2387
2388 tst = BOZO_DeleteCellHost(b_handle->server, (char *)hostName);
2389
2390 if (tst == 0) {
2391 rc = 1;
2392 }
2393
2394 fail_bos_HostDelete:
2395
2396 if (st != NULL) {
2397 *st = tst;
2398 }
2399 return rc;
2400 }
2401
2402 /*
2403 * The iterator functions and data for the host retrieval functions
2404 */
2405
2406 typedef struct host_get {
2407 int next;
2408 struct rx_connection *server;
2409 char host[CACHED_ITEMS][BOS_MAX_NAME_LEN];
2410 } host_get_t, *host_get_p;
2411
2412 static int
2413 GetHostRPC(void *rpc_specific, int slot, int *last_item,
2414 int *last_item_contains_data, afs_status_p st)
2415 {
2416 int rc = 0;
2417 afs_status_t tst = 0;
2418 host_get_p host = (host_get_p) rpc_specific;
2419 char *ptr = (char *)&host->host[slot];
2420
2421 tst = BOZO_GetCellHost(host->server, host->next++, &ptr);
2422
2423 if (tst == 0) {
2424 rc = 1;
2425 } else if (tst == BZDOM) {
2426 tst = 0;
2427 rc = 1;
2428 *last_item = 1;
2429 *last_item_contains_data = 0;
2430 }
2431
2432 if (st != NULL) {
2433 *st = tst;
2434 }
2435 return rc;
2436 }
2437
2438 static int
2439 GetHostFromCache(void *rpc_specific, int slot, void *dest, afs_status_p st)
2440 {
2441 int rc = 0;
2442 afs_status_t tst = 0;
2443 host_get_p host = (host_get_p) rpc_specific;
2444
2445 strcpy((char *)dest, (char *)&host->host[slot]);
2446 rc = 1;
2447
2448 if (st != NULL) {
2449 *st = tst;
2450 }
2451 return rc;
2452 }
2453
2454 /*
2455 * bos_HostGetBegin - begin iterating over the hosts in a cell
2456 * at a particular bos server.
2457 *
2458 * PARAMETERS
2459 *
2460 * IN serverHandle - a previously opened serverHandle.
2461 *
2462 * OUT iter - an iterator that can be passed to bos_HostGetNext
2463 * to retrieve the process names.
2464 *
2465 * LOCKS
2466 *
2467 * No locks are obtained or released by this function
2468 *
2469 * RETURN CODES
2470 *
2471 * Returns != 0 upon successful completion.
2472 *
2473 */
2474
2475 int ADMINAPI
2476 bos_HostGetBegin(const void *serverHandle, void **iterationIdP,
2477 afs_status_p st)
2478 {
2479 int rc = 0;
2480 afs_status_t tst = 0;
2481 bos_server_p b_handle = (bos_server_p) serverHandle;
2482 afs_admin_iterator_p iter = malloc(sizeof(afs_admin_iterator_t));
2483 host_get_p host = malloc(sizeof(host_get_t));
2484
2485 if (!isValidServerHandle(b_handle, &tst)) {
2486 goto fail_bos_HostGetBegin;
2487 }
2488
2489 if (iterationIdP == NULL) {
2490 tst = ADMITERATIONIDPNULL;
2491 goto fail_bos_HostGetBegin;
2492 }
2493
2494 if ((iter == NULL) || (host == NULL)) {
2495 tst = ADMNOMEM;
2496 goto fail_bos_HostGetBegin;
2497 }
2498
2499 host->next = 0;
2500 host->server = b_handle->server;
2501
2502 if (IteratorInit
2503 (iter, (void *)host, GetHostRPC, GetHostFromCache, NULL, NULL,
2504 &tst)) {
2505 *iterationIdP = (void *)iter;
2506 rc = 1;
2507 }
2508
2509 fail_bos_HostGetBegin:
2510
2511 if (rc == 0) {
2512 if (iter != NULL) {
2513 free(iter);
2514 }
2515 if (host != NULL) {
2516 free(host);
2517 }
2518 }
2519
2520 if (st != NULL) {
2521 *st = tst;
2522 }
2523 return rc;
2524 }
2525
2526 /*
2527 * bos_HostGetNext - retrieve the next host
2528 * from the bos server.
2529 *
2530 * PARAMETERS
2531 *
2532 * IN iterationId - an iterator previously returned by
2533 * bos_HostGetBegin
2534 *
2535 * OUT hostName - upon successful completion contains the next host
2536 * retrieved from the server.
2537 *
2538 * LOCKS
2539 *
2540 * No locks are obtained or released by this function
2541 *
2542 * RETURN CODES
2543 *
2544 * Returns != 0 upon successful completion.
2545 *
2546 */
2547
2548 int ADMINAPI
2549 bos_HostGetNext(const void *iterationId, char *hostName, afs_status_p st)
2550 {
2551 int rc = 0;
2552 afs_status_t tst = 0;
2553 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
2554
2555 if (iterationId == NULL) {
2556 tst = ADMITERATIONIDPNULL;
2557 goto fail_bos_HostGetNext;
2558 }
2559
2560 if (hostName == NULL) {
2561 tst = ADMBOSHOSTNAMENULL;
2562 goto fail_bos_HostGetNext;
2563 }
2564
2565 rc = IteratorNext(iter, (void *)hostName, &tst);
2566
2567 fail_bos_HostGetNext:
2568
2569 if (st != NULL) {
2570 *st = tst;
2571 }
2572 return rc;
2573 }
2574
2575 /*
2576 * bos_HostGetDone - finish using a host iterator.
2577 *
2578 * PARAMETERS
2579 *
2580 * IN iterationId - an iterator previously returned by
2581 * bos_HostGetBegin
2582 *
2583 * LOCKS
2584 *
2585 * No locks are obtained or released by this function
2586 *
2587 * RETURN CODES
2588 *
2589 * Returns != 0 upon successful completion.
2590 *
2591 */
2592
2593 int ADMINAPI
2594 bos_HostGetDone(const void *iterationId, afs_status_p st)
2595 {
2596 int rc = 0;
2597 afs_status_t tst = 0;
2598 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
2599
2600 if (iterationId == NULL) {
2601 tst = ADMITERATIONIDPNULL;
2602 goto fail_bos_HostGetDone;
2603 }
2604
2605 rc = IteratorDone(iter, &tst);
2606
2607 fail_bos_HostGetDone:
2608
2609 if (st != NULL) {
2610 *st = tst;
2611 }
2612 return rc;
2613 }
2614
2615 /*
2616 * bos_ExecutableCreate - create a new executable at the bos server.
2617 *
2618 * PARAMETERS
2619 *
2620 * IN serverHandle - a previously opened serverHandle.
2621 *
2622 * IN sourceFile - the executable to install at the bos server.
2623 *
2624 * IN destFile - the location where the executable will be installed.
2625 *
2626 * LOCKS
2627 *
2628 * No locks are obtained or released by this function
2629 *
2630 * RETURN CODES
2631 *
2632 * Returns != 0 upon successful completion.
2633 *
2634 */
2635
2636 int ADMINAPI
2637 bos_ExecutableCreate(const void *serverHandle, const char *sourceFile,
2638 const char *destFile, afs_status_p st)
2639 {
2640 int rc = 0;
2641 afs_status_t tst = 0;
2642 bos_server_p b_handle = (bos_server_p) serverHandle;
2643 int fd;
2644 struct stat estat;
2645 struct rx_call *tcall;
2646
2647 /*
2648 * Validate arguments
2649 */
2650
2651 if (!isValidServerHandle(b_handle, &tst)) {
2652 goto fail_bos_ExecutableCreate;
2653 }
2654
2655 if ((sourceFile == NULL) || (*sourceFile == 0)) {
2656 tst = ADMBOSSOURCEFILENULL;
2657 goto fail_bos_ExecutableCreate;
2658 }
2659
2660 if ((destFile == NULL) || (*destFile == 0)) {
2661 tst = ADMBOSDESTFILENULL;
2662 goto fail_bos_ExecutableCreate;
2663 }
2664
2665 /*
2666 * Open the file locally and compute its size
2667 */
2668
2669 fd = open(sourceFile, O_RDONLY);
2670
2671 if (fd < 0) {
2672 tst = ADMBOSCANTOPENSOURCEFILE;
2673 goto fail_bos_ExecutableCreate;
2674 }
2675
2676 if (fstat(fd, &estat)) {
2677 tst = ADMBOSCANTSTATSOURCEFILE;
2678 goto fail_bos_ExecutableCreate;
2679 }
2680
2681 /*
2682 * Start a split rpc to the bos server.
2683 */
2684
2685 tcall = rx_NewCall(b_handle->server);
2686
2687 tst =
2688 StartBOZO_Install(tcall, (char *)destFile, estat.st_size,
2689 (afs_int32) estat.st_mode, estat.st_mtime);
2690
2691 if (tst) {
2692 tst = rx_EndCall(tcall, tst);
2693 goto fail_bos_ExecutableCreate;
2694 }
2695
2696 /*
2697 * Copy the data to the server
2698 */
2699
2700 while (1) {
2701 char tbuffer[512];
2702 ssize_t len;
2703 len = read(fd, tbuffer, sizeof(tbuffer));
2704 if (len < 0) {
2705 tst = ADMBOSCANTREADSOURCEFILE;
2706 rx_EndCall(tcall, len);
2707 goto fail_bos_ExecutableCreate;
2708 }
2709 if (len == 0) {
2710 tst = 0;
2711 break;
2712 }
2713 tst = rx_Write(tcall, tbuffer, len);
2714 if (tst != len) {
2715 tst = ADMBOSSENDSOURCEFILE;
2716 rx_EndCall(tcall, tst);
2717 goto fail_bos_ExecutableCreate;
2718 }
2719 }
2720
2721 /*
2722 * Terminate the rpc to the server
2723 */
2724
2725 tst = rx_EndCall(tcall, tst);
2726
2727 if (tst == 0) {
2728 rc = 1;
2729 }
2730
2731 fail_bos_ExecutableCreate:
2732
2733 if (st != NULL) {
2734 *st = tst;
2735 }
2736 return rc;
2737 }
2738
2739 /*
2740 * bos_ExecutableRevert - revert an executable to a previous .BAK version.
2741 *
2742 * PARAMETERS
2743 *
2744 * IN serverHandle - a previously opened serverHandle.
2745 *
2746 * IN execFile - the executable to revert at the bos server.
2747 *
2748 * LOCKS
2749 *
2750 * No locks are obtained or released by this function
2751 *
2752 * RETURN CODES
2753 *
2754 * Returns != 0 upon successful completion.
2755 *
2756 */
2757
2758 int ADMINAPI
2759 bos_ExecutableRevert(const void *serverHandle, const char *execFile,
2760 afs_status_p st)
2761 {
2762 int rc = 0;
2763 afs_status_t tst = 0;
2764 bos_server_p b_handle = (bos_server_p) serverHandle;
2765
2766 if (!isValidServerHandle(b_handle, &tst)) {
2767 goto fail_bos_ExecutableRevert;
2768 }
2769
2770 if ((execFile == NULL) || (*execFile == 0)) {
2771 tst = ADMBOSEXECFILENULL;
2772 goto fail_bos_ExecutableRevert;
2773 }
2774
2775 tst = BOZO_UnInstall(b_handle->server, (char *)execFile);
2776
2777 if (tst == 0) {
2778 rc = 1;
2779 }
2780
2781 fail_bos_ExecutableRevert:
2782
2783 if (st != NULL) {
2784 *st = tst;
2785 }
2786 return rc;
2787 }
2788
2789 /*
2790 * bos_ExecutableTimestampGet - get the last mod times for an executable,
2791 * the .BAK version of the executable, and the .OLD version of the
2792 * executable if they exist.
2793 *
2794 * PARAMETERS
2795 *
2796 * IN serverHandle - a previously opened serverHandle.
2797 *
2798 * IN execFile - the executable to revert at the bos server.
2799 *
2800 * LOCKS
2801 *
2802 * No locks are obtained or released by this function
2803 *
2804 * RETURN CODES
2805 *
2806 * Returns != 0 upon successful completion.
2807 *
2808 */
2809
2810 int ADMINAPI
2811 bos_ExecutableTimestampGet(const void *serverHandle, const char *execFile,
2812 afs_int32 *newTime, afs_int32 *oldTime,
2813 afs_int32 *bakTime, afs_status_p st)
2814 {
2815 int rc = 0;
2816 afs_status_t tst = 0;
2817 bos_server_p b_handle = (bos_server_p) serverHandle;
2818
2819 if (!isValidServerHandle(b_handle, &tst)) {
2820 goto fail_bos_ExecutableTimestampGet;
2821 }
2822
2823 if ((execFile == NULL) || (*execFile == 0)) {
2824 tst = ADMBOSEXECFILENULL;
2825 goto fail_bos_ExecutableTimestampGet;
2826 }
2827
2828 if (newTime == NULL) {
2829 tst = ADMBOSNEWTIMENULL;
2830 goto fail_bos_ExecutableTimestampGet;
2831 }
2832
2833 if (oldTime == NULL) {
2834 tst = ADMBOSOLDTIMENULL;
2835 goto fail_bos_ExecutableTimestampGet;
2836 }
2837
2838 if (bakTime == NULL) {
2839 tst = ADMBOSBAKTIMENULL;
2840 goto fail_bos_ExecutableTimestampGet;
2841 }
2842
2843 tst =
2844 BOZO_GetDates(b_handle->server, (char *)execFile, newTime, bakTime, oldTime);
2845
2846 if (tst == 0) {
2847 rc = 1;
2848 }
2849
2850 fail_bos_ExecutableTimestampGet:
2851
2852 if (st != NULL) {
2853 *st = tst;
2854 }
2855 return rc;
2856 }
2857
2858 /*
2859 * bos_ExecutablePrune - prune the bak, old, and core files off a server
2860 * machine.
2861 *
2862 * PARAMETERS
2863 *
2864 * IN serverHandle - a previously opened serverHandle.
2865 *
2866 * IN oldFiles - prune .OLD files.
2867 *
2868 * IN bakFiles - prune .BAK files.
2869 *
2870 * IN coreFiles - prune core files.
2871 *
2872 * LOCKS
2873 *
2874 * No locks are obtained or released by this function
2875 *
2876 * RETURN CODES
2877 *
2878 * Returns != 0 upon successful completion.
2879 *
2880 */
2881
2882 int ADMINAPI
2883 bos_ExecutablePrune(const void *serverHandle, bos_Prune_t oldFiles,
2884 bos_Prune_t bakFiles, bos_Prune_t coreFiles,
2885 afs_status_p st)
2886 {
2887 int rc = 0;
2888 afs_status_t tst = 0;
2889 bos_server_p b_handle = (bos_server_p) serverHandle;
2890 afs_int32 flags = 0;
2891
2892 if (!isValidServerHandle(b_handle, &tst)) {
2893 goto fail_bos_ExecutablePrune;
2894 }
2895
2896 if (oldFiles == BOS_PRUNE) {
2897 flags |= BOZO_PRUNEOLD;
2898 }
2899
2900 if (bakFiles == BOS_PRUNE) {
2901 flags |= BOZO_PRUNEBAK;
2902 }
2903
2904 if (coreFiles == BOS_PRUNE) {
2905 flags |= BOZO_PRUNECORE;
2906 }
2907
2908 tst = BOZO_Prune(b_handle->server, flags);
2909
2910 if (tst == 0) {
2911 rc = 1;
2912 }
2913
2914 fail_bos_ExecutablePrune:
2915
2916 if (st != NULL) {
2917 *st = tst;
2918 }
2919 return rc;
2920 }
2921
2922 /*
2923 * bos_ExecutableRestartTimeSet - set the restart time of the bos server
2924 * machine.
2925 *
2926 * PARAMETERS
2927 *
2928 * IN serverHandle - a previously opened serverHandle.
2929 *
2930 * IN type - specifies either weekly restart or daily restart time.
2931 *
2932 * IN time - the time to begin restarts.
2933 *
2934 * LOCKS
2935 *
2936 * No locks are obtained or released by this function
2937 *
2938 * RETURN CODES
2939 *
2940 * Returns != 0 upon successful completion.
2941 *
2942 */
2943
2944 int ADMINAPI
2945 bos_ExecutableRestartTimeSet(const void *serverHandle, bos_Restart_t type,
2946 bos_RestartTime_t time, afs_status_p st)
2947 {
2948 int rc = 0;
2949 afs_status_t tst = 0;
2950 bos_server_p b_handle = (bos_server_p) serverHandle;
2951 afs_int32 restartType = 0;
2952 struct bozo_netKTime restartTime;
2953
2954 if (!isValidServerHandle(b_handle, &tst)) {
2955 goto fail_bos_ExecutableRestartTimeSet;
2956 }
2957
2958 if (type == BOS_RESTART_WEEKLY) {
2959 restartType = 1;
2960 } else {
2961 restartType = 2;
2962 }
2963
2964 if ((time.mask & BOS_RESTART_TIME_HOUR)
2965 && ((time.hour < 0) || (time.hour > 23))) {
2966 tst = ADMBOSHOURINVALID;
2967 goto fail_bos_ExecutableRestartTimeSet;
2968 }
2969
2970 if ((time.mask & BOS_RESTART_TIME_MINUTE)
2971 && ((time.min < 0) || (time.min > 60))) {
2972 tst = ADMBOSMINUTEINVALID;
2973 goto fail_bos_ExecutableRestartTimeSet;
2974 }
2975
2976 if ((time.mask & BOS_RESTART_TIME_SECOND)
2977 && ((time.sec < 0) || (time.sec > 60))) {
2978 tst = ADMBOSSECONDINVALID;
2979 goto fail_bos_ExecutableRestartTimeSet;
2980 }
2981
2982 if ((time.mask & BOS_RESTART_TIME_DAY)
2983 && ((time.day < 0) || (time.day > 6))) {
2984 tst = ADMBOSDAYINVALID;
2985 goto fail_bos_ExecutableRestartTimeSet;
2986 }
2987
2988 restartTime.mask = time.mask;
2989 restartTime.hour = time.hour;
2990 restartTime.min = time.min;
2991 restartTime.sec = time.sec;
2992 restartTime.day = time.day;
2993
2994 tst = BOZO_SetRestartTime(b_handle->server, restartType, &restartTime);
2995
2996 if (tst == 0) {
2997 rc = 1;
2998 }
2999
3000 fail_bos_ExecutableRestartTimeSet:
3001
3002 if (st != NULL) {
3003 *st = tst;
3004 }
3005 return rc;
3006 }
3007
3008 /*
3009 * bos_ExecutableRestartTimeGet - get the restart time of the bos server
3010 * machine.
3011 *
3012 * PARAMETERS
3013 *
3014 * IN serverHandle - a previously opened serverHandle.
3015 *
3016 * IN type - specifies either weekly restart or daily restart time.
3017 *
3018 * OUT timeP - the time to begin restarts.
3019 *
3020 * LOCKS
3021 *
3022 * No locks are obtained or released by this function
3023 *
3024 * RETURN CODES
3025 *
3026 * Returns != 0 upon successful completion.
3027 *
3028 */
3029
3030 int ADMINAPI
3031 bos_ExecutableRestartTimeGet(const void *serverHandle, bos_Restart_t type,
3032 bos_RestartTime_p timeP, afs_status_p st)
3033 {
3034 int rc = 0;
3035 afs_status_t tst = 0;
3036 bos_server_p b_handle = (bos_server_p) serverHandle;
3037 afs_int32 restartType = 0;
3038 struct bozo_netKTime restartTime;
3039
3040 if (!isValidServerHandle(b_handle, &tst)) {
3041 goto fail_bos_ExecutableRestartTimeGet;
3042 }
3043
3044 if (timeP == NULL) {
3045 tst = ADMBOSTIMEPNULL;
3046 goto fail_bos_ExecutableRestartTimeGet;
3047 }
3048
3049 if (type == BOS_RESTART_WEEKLY) {
3050 restartType = 1;
3051 } else {
3052 restartType = 2;
3053 }
3054
3055 tst = BOZO_GetRestartTime(b_handle->server, restartType, &restartTime);
3056
3057 if (tst != 0) {
3058 goto fail_bos_ExecutableRestartTimeGet;
3059 }
3060
3061 timeP->mask = restartTime.mask;
3062 timeP->hour = restartTime.hour;
3063 timeP->min = restartTime.min;
3064 timeP->sec = restartTime.sec;
3065 timeP->day = restartTime.day;
3066 rc = 1;
3067
3068 fail_bos_ExecutableRestartTimeGet:
3069
3070 if (st != NULL) {
3071 *st = tst;
3072 }
3073 return rc;
3074 }
3075
3076 /*
3077 * bos_LogGet - get a log file from the bos server machine.
3078 *
3079 * PARAMETERS
3080 *
3081 * IN serverHandle - a previously opened serverHandle.
3082 *
3083 * IN log - the log file to retrieve.
3084 *
3085 * IN/OUT logBufferSizeP - the length of the logData buffer on input,
3086 * and upon successful completion, the length of data stored in the buffer.
3087 *
3088 * OUT logData - the retrieved data upon successful completion.
3089 *
3090 * LOCKS
3091 *
3092 * No locks are obtained or released by this function
3093 *
3094 * RETURN CODES
3095 *
3096 * Returns != 0 upon successful completion.
3097 *
3098 */
3099
3100 int ADMINAPI
3101 bos_LogGet(const void *serverHandle, const char *log,
3102 unsigned long *logBufferSizeP, char *logData, afs_status_p st)
3103 {
3104 int rc = 0;
3105 afs_status_t tst = 0;
3106 bos_server_p b_handle = (bos_server_p) serverHandle;
3107 struct rx_call *tcall = NULL;
3108 afs_int32 error;
3109 char buffer;
3110 int have_call = 0;
3111 unsigned long bytes_read = 0;
3112
3113 /*
3114 * Validate parameters
3115 */
3116
3117 if (!isValidServerHandle(b_handle, &tst)) {
3118 goto fail_bos_LogGet;
3119 }
3120
3121 if ((log == NULL) || (*log == 0)) {
3122 tst = ADMBOSLOGNULL;
3123 goto fail_bos_LogGet;
3124 }
3125
3126 if (logBufferSizeP == NULL) {
3127 tst = ADMBOSLOGBUFFERSIZEPNULL;
3128 goto fail_bos_LogGet;
3129 }
3130
3131 if (logData == NULL) {
3132 tst = ADMBOSLOGDATANULL;
3133 goto fail_bos_LogGet;
3134 }
3135
3136 /*
3137 * Begin to retrieve the data
3138 */
3139
3140 tcall = rx_NewCall(b_handle->server);
3141 have_call = 1;
3142 tst = StartBOZO_GetLog(tcall, (char *) log);
3143
3144 if (tst != 0) {
3145 goto fail_bos_LogGet;
3146 }
3147
3148 /*
3149 * Read the log file data
3150 */
3151
3152 while (1) {
3153 error = rx_Read(tcall, &buffer, 1);
3154 if (error != 1) {
3155 tst = ADMBOSLOGFILEERROR;
3156 goto fail_bos_LogGet;
3157 }
3158
3159 /*
3160 * check for the end of the log
3161 */
3162
3163 if (buffer == 0) {
3164 *logBufferSizeP = bytes_read;
3165 break;
3166 }
3167
3168 /*
3169 * We've successfully read another byte, copy it to logData
3170 * if there's room
3171 */
3172
3173 bytes_read++;
3174 if (bytes_read <= *logBufferSizeP) {
3175 *logData++ = buffer;
3176 } else {
3177 tst = ADMMOREDATA;
3178 }
3179 }
3180 if (tst == 0) {
3181 rc = 1;
3182 }
3183
3184 fail_bos_LogGet:
3185
3186 if (have_call) {
3187 tst = rx_EndCall(tcall, 0);
3188 }
3189
3190 if (st != NULL) {
3191 *st = tst;
3192 }
3193 return rc;
3194 }
3195
3196 /*
3197 * bos_AuthSet - set the authorization level required at the bos server.
3198 *
3199 * PARAMETERS
3200 *
3201 * IN serverHandle - a previously opened serverHandle.
3202 *
3203 * IN auth - specifies the new auth level.
3204 *
3205 * LOCKS
3206 *
3207 * No locks are obtained or released by this function
3208 *
3209 * RETURN CODES
3210 *
3211 * Returns != 0 upon successful completion.
3212 *
3213 */
3214
3215 int ADMINAPI
3216 bos_AuthSet(const void *serverHandle, bos_Auth_t auth, afs_status_p st)
3217 {
3218 int rc = 0;
3219 afs_status_t tst = 0;
3220 bos_server_p b_handle = (bos_server_p) serverHandle;
3221 afs_int32 level = 0;
3222
3223 if (!isValidServerHandle(b_handle, &tst)) {
3224 goto fail_bos_AuthSet;
3225 }
3226
3227 if (auth == BOS_AUTH_REQUIRED) {
3228 level = 0;
3229 } else {
3230 level = 1;
3231 }
3232
3233 tst = BOZO_SetNoAuthFlag(b_handle->server, level);
3234
3235 if (tst == 0) {
3236 rc = 1;
3237 }
3238
3239 fail_bos_AuthSet:
3240
3241 if (st != NULL) {
3242 *st = tst;
3243 }
3244 return rc;
3245 }
3246
3247 /*
3248 * bos_CommandExecute - execute a command at the bos server.
3249 *
3250 * PARAMETERS
3251 *
3252 * IN serverHandle - a previously opened serverHandle.
3253 *
3254 * IN command - the command to execute.
3255 *
3256 * LOCKS
3257 *
3258 * No locks are obtained or released by this function
3259 *
3260 * RETURN CODES
3261 *
3262 * Returns != 0 upon successful completion.
3263 *
3264 */
3265
3266 int ADMINAPI
3267 bos_CommandExecute(const void *serverHandle, const char *command,
3268 afs_status_p st)
3269 {
3270 int rc = 0;
3271 afs_status_t tst = 0;
3272 bos_server_p b_handle = (bos_server_p) serverHandle;
3273
3274 if (!isValidServerHandle(b_handle, &tst)) {
3275 goto fail_bos_CommandExecute;
3276 }
3277
3278 if ((command == NULL) || (*command == 0)) {
3279 tst = ADMBOSCOMMANDNULL;
3280 goto fail_bos_CommandExecute;
3281 }
3282
3283 tst = BOZO_Exec(b_handle->server, (char *) command);
3284
3285 if (tst == 0) {
3286 rc = 1;
3287 }
3288
3289 fail_bos_CommandExecute:
3290
3291 if (st != NULL) {
3292 *st = tst;
3293 }
3294 return rc;
3295 }
3296
3297 /*
3298 * bos_Salvage - perform a remote salvage operation.
3299 *
3300 * PARAMETERS
3301 *
3302 * IN cellHandle - a previously opened cellHandle.
3303 *
3304 * IN serverHandle - a previously opened serverHandle.
3305 *
3306 * IN partitionName - the partition to salvage. Can be null.
3307 *
3308 * IN volumeName - the volume to salvage. Can be null, if non-null,
3309 * partitionName cannot be null.
3310 *
3311 * IN numSalvagers - the number of salvage processes to run in parallel.
3312 *
3313 * IN tmpDir - directory to place temporary files. Can be null.
3314 *
3315 * IN logFile - file where salvage log will be written. Can be null.
3316 *
3317 * IN force - sets salvager -force flag.
3318 *
3319 * IN salvageDamagedVolumes - sets salvager -oktozap flag.
3320 *
3321 * IN writeInodes - sets salvager -inodes flag.
3322 *
3323 * IN writeRootInodes - sets salvager -rootinodes flag.
3324 *
3325 * IN forceDirectory - sets salvager -salvagedirs flag.
3326 *
3327 * IN forceBlockRead - sets salvager -blockread flag.
3328 *
3329 * LOCKS
3330 *
3331 * No locks are obtained or released by this function
3332 *
3333 * RETURN CODES
3334 *
3335 * Returns != 0 upon successful completion.
3336 *
3337 */
3338
3339 #define INITIAL_LOG_LEN 4096
3340
3341 int ADMINAPI
3342 bos_Salvage(const void *cellHandle, const void *serverHandle,
3343 const char *partitionName, const char *volumeName,
3344 int numSalvagers, const char *tmpDir, const char *logFile,
3345 vos_force_t force,
3346 bos_SalvageDamagedVolumes_t salvageDamagedVolumes,
3347 bos_WriteInodes_t writeInodes,
3348 bos_WriteRootInodes_t writeRootInodes,
3349 bos_ForceDirectory_t forceDirectory,
3350 bos_ForceBlockRead_t forceBlockRead, afs_status_p st)
3351 {
3352 int rc = 0;
3353 afs_status_t tst = 0;
3354 bos_server_p b_handle = (bos_server_p) serverHandle;
3355 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
3356 int have_partition = 0;
3357 int have_volume = 0;
3358 unsigned int part = 0;
3359 int try_to_stop_fileserver = 0;
3360 bos_ProcessType_t procType;
3361 bos_ProcessInfo_t procInfo;
3362 FILE *log = NULL;
3363 char command[BOS_MAX_NAME_LEN];
3364 int command_len = 0;
3365 int poll_rc;
3366 char *logData = NULL;
3367 unsigned long logLen = INITIAL_LOG_LEN;
3368
3369 /*
3370 * Validate arguments
3371 */
3372
3373 if (!IsValidCellHandle(c_handle, &tst)) {
3374 goto fail_bos_Salvage;
3375 }
3376
3377 if (!isValidServerHandle(b_handle, &tst)) {
3378 goto fail_bos_Salvage;
3379 }
3380
3381 if (c_handle->vos_valid == 0) {
3382 tst = ADMBOSCELLHANDLENOVOS;
3383 goto fail_bos_Salvage;
3384 }
3385
3386 if ((partitionName != NULL) && (*partitionName != 0)) {
3387 if (!vos_PartitionNameToId(partitionName, &part, &tst)) {
3388 goto fail_bos_Salvage;
3389 }
3390 have_partition = 1;
3391 }
3392
3393 if ((volumeName != NULL) && (*volumeName != 0)) {
3394 if (!have_partition) {
3395 tst = ADMBOSSALVAGEVOLUME;
3396 goto fail_bos_Salvage;
3397 }
3398 have_volume = 1;
3399 }
3400
3401 if ((logFile != NULL) && (*logFile != 0)) {
3402 log = fopen(logFile, "w");
3403 if (!log) {
3404 tst = ADMBOSSALVAGEBADLOG;
3405 goto fail_bos_Salvage;
3406 }
3407 }
3408
3409 /*
3410 * If we are salvaging more than a single volume, stop the fileserver
3411 */
3412
3413 if (!have_volume) {
3414 try_to_stop_fileserver = 1;
3415 }
3416
3417 /*
3418 * Only try to stop the fileserver if it is running
3419 */
3420
3421 if (try_to_stop_fileserver) {
3422 if (bos_ProcessInfoGet
3423 (serverHandle, "fs", &procType, &procInfo, &tst)) {
3424 if (procInfo.processGoal != BOS_PROCESS_RUNNING) {
3425 try_to_stop_fileserver = 0;
3426 }
3427 }
3428 }
3429
3430 /*
3431 * Make the call to stop the fileserver and wait for it to shutdown
3432 */
3433
3434 if (try_to_stop_fileserver) {
3435 if (!bos_ProcessExecutionStateSetTemporary
3436 (serverHandle, "fs", BOS_PROCESS_STOPPED, &tst)) {
3437 goto fail_bos_Salvage;
3438 }
3439 bos_ProcessAllWaitTransition(serverHandle, &tst);
3440 }
3441
3442 /*
3443 * Create the salvage command line arguments
3444 */
3445
3446 command_len =
3447 sprintf(command, "%s ", AFSDIR_CANONICAL_SERVER_SALVAGER_FILEPATH);
3448 if (have_partition) {
3449 command_len +=
3450 sprintf(&command[command_len], "-partition %s ", partitionName);
3451 }
3452
3453 if (have_volume) {
3454 command_len +=
3455 sprintf(&command[command_len], "-volumeid %s ", volumeName);
3456 }
3457
3458 if (salvageDamagedVolumes == BOS_DONT_SALVAGE_DAMAGED_VOLUMES) {
3459 command_len += sprintf(&command[command_len], "-nowrite ");
3460 }
3461
3462 if (writeInodes == BOS_SALVAGE_WRITE_INODES) {
3463 command_len += sprintf(&command[command_len], "-inodes ");
3464 }
3465
3466 if (force == VOS_FORCE) {
3467 command_len += sprintf(&command[command_len], "-force ");
3468 }
3469
3470 if (writeRootInodes == BOS_SALVAGE_WRITE_ROOT_INODES) {
3471 command_len += sprintf(&command[command_len], "-rootinodes ");
3472 }
3473
3474 if (forceDirectory == BOS_SALVAGE_FORCE_DIRECTORIES) {
3475 command_len += sprintf(&command[command_len], "-salvagedirs ");
3476 }
3477
3478 if (forceBlockRead == BOS_SALVAGE_FORCE_BLOCK_READS) {
3479 command_len += sprintf(&command[command_len], "-blockreads ");
3480 }
3481
3482 command_len +=
3483 sprintf(&command[command_len], "-parallel %d ", numSalvagers);
3484
3485 if ((tmpDir != NULL) && (*tmpDir != 0)) {
3486 command_len += sprintf(&command[command_len], "-tmpdir %s ", tmpDir);
3487 }
3488
3489 if (command_len > BOS_MAX_NAME_LEN) {
3490 tst = ADMBOSSALVAGEBADOPTIONS;
3491 goto fail_bos_Salvage;
3492 }
3493
3494 /*
3495 * Create the process at the bosserver and wait until it completes
3496 */
3497
3498 if (!bos_ProcessCreate
3499 (serverHandle, "salvage-tmp", BOS_PROCESS_CRON, command, "now", 0,
3500 &tst)) {
3501 goto fail_bos_Salvage;
3502 }
3503
3504 while ((poll_rc =
3505 bos_ProcessInfoGet(serverHandle, "salvage-tmp", &procType,
3506 &procInfo, &tst))) {
3507 sleep(5);
3508 }
3509
3510 if (tst != BZNOENT) {
3511 goto fail_bos_Salvage;
3512 }
3513
3514 /*
3515 * Print out the salvage log if required by the user
3516 */
3517
3518 if (log != NULL) {
3519
3520 logData = malloc(INITIAL_LOG_LEN);
3521 if (!logData) {
3522 tst = ADMNOMEM;
3523 goto fail_bos_Salvage;
3524 }
3525
3526 while (!bos_LogGet
3527 (serverHandle, AFSDIR_CANONICAL_SERVER_SLVGLOG_FILEPATH,
3528 &logLen, logData, &tst)) {
3529 if (logLen > INITIAL_LOG_LEN) {
3530 logData = realloc(logData, (logLen + (logLen / 10)));
3531 if (logData == NULL) {
3532 tst = ADMNOMEM;
3533 goto fail_bos_Salvage;
3534 }
3535 } else {
3536 goto fail_bos_Salvage;
3537 }
3538 }
3539 fprintf(log, "SalvageLog:\n%s", logData);
3540 }
3541
3542 /*
3543 * Restart the fileserver if we had stopped it previously
3544 */
3545
3546 if (try_to_stop_fileserver) {
3547 try_to_stop_fileserver = 0;
3548 if (!bos_ProcessExecutionStateSetTemporary
3549 (serverHandle, "fs", BOS_PROCESS_RUNNING, &tst)) {
3550 goto fail_bos_Salvage;
3551 }
3552 }
3553 rc = 1;
3554
3555 fail_bos_Salvage:
3556
3557 if (log != NULL) {
3558 fclose(log);
3559 }
3560
3561 if (logData != NULL) {
3562 free(logData);
3563 }
3564
3565 if (try_to_stop_fileserver) {
3566 bos_ProcessExecutionStateSetTemporary(serverHandle, "fs",
3567 BOS_PROCESS_RUNNING, 0);
3568 }
3569
3570 if (st != NULL) {
3571 *st = tst;
3572 }
3573 return rc;
3574 }