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 #include <afs/param.h>
11 #include <afsconfig.h>
25 #include <sys/types.h>
26 #include <sys/socket.h>
28 #include <netinet/in.h>
29 #include <arpa/inet.h>
32 #include "afs_vosAdmin.h"
33 #include "../adminutil/afs_AdminInternal.h"
34 #include <afs/afs_utilAdmin.h>
35 #include <afs/vlserver.h>
36 #include <afs/volser.h>
37 #include <afs/volint.h>
38 #include <afs/partition.h>
42 #include "lockprocs.h"
44 extern int VL_GetAddrsU();
46 typedef struct file_server {
49 struct rx_connection *serv;
51 } file_server_t, *file_server_p;
54 * IsValidServerHandle - test a server handle for validity.
58 * IN serverHandle - the serverHandle to be validated.
62 * No locks are obtained or released by this function
66 * Returns != 0 upon successful completion.
69 static int IsValidServerHandle(
70 file_server_p serverHandle,
76 if (serverHandle == NULL) {
77 tst = ADMVOSSERVERHANDLENULL;
78 goto fail_IsValidServerHandle;
81 if (serverHandle->is_valid != 1) {
82 tst = ADMVOSSERVERHANDLEINVALID;
83 goto fail_IsValidServerHandle;
86 if ((serverHandle->begin_magic != BEGIN_MAGIC) ||
87 (serverHandle->end_magic != END_MAGIC)) {
88 tst = ADMVOSSERVERHANDLEBADMAGIC;
89 goto fail_IsValidServerHandle;
93 fail_IsValidServerHandle:
103 * IsValidCellHandle - verify that a cell handle can be used to make vos
108 * IN cellHandle - the cellHandle to be validated.
112 * No locks are obtained or released by this function
116 * Returns != 0 upon successful completion.
119 static int IsValidCellHandle(
120 afs_cell_handle_p cellHandle,
124 afs_status_t tst = 0;
126 if (!CellHandleIsValid((void *) cellHandle, &tst)) {
127 goto fail_IsValidCellHandle;
130 if (cellHandle->vos_valid == 0) {
131 tst = ADMVOSCELLHANDLEINVALIDVOS;
132 goto fail_IsValidCellHandle;
136 fail_IsValidCellHandle:
144 /* set <server> and <part> to the correct values depending on
145 * <voltype> and <entry> */
146 static void GetServerAndPart (
147 struct nvldbentry *entry,
153 int i, istart, vtype;
158 /* Doesn't check for non-existance of backup volume */
159 if ((voltype == RWVOL) || (voltype == BACKVOL)) {
161 istart = 0; /* seach the entire entry */
164 /* Seach from beginning of entry or pick up where we left off */
165 istart = ((*previdx < 0) ? 0 : *previdx+1);
168 for (i = istart; i < entry->nServers; i++) {
169 if (entry->serverFlags[i] & vtype) {
170 *server = entry->serverNumber[i];
171 *part = entry->serverPartition[i];
177 /* Didn't find any, return -1 */
183 * vos_BackupVolumeCreate - create a backup volume for a volume.
187 * IN cellHandle - a previously opened cellHandle that corresponds
188 * to the cell where volume exists.
190 * IN callBack - a call back function pointer that may be called to report
191 * status information. Can be null.
193 * IN volumeId - the volume to create the back up for.
197 * No locks are obtained or released by this function
201 * Returns != 0 upon successful completion.
204 int ADMINAPI vos_BackupVolumeCreate(
205 const void *cellHandle,
206 vos_MessageCallBack_t callBack,
207 unsigned int volumeId,
211 afs_status_t tst = 0;
212 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
213 struct nvldbentry rw_vol_entry;
215 afs_int32 rw_partition;
216 afs_int32 rw_vol_type;
217 struct nvldbentry bk_vol_entry;
219 afs_int32 bk_partition;
220 afs_int32 bk_vol_type;
227 if (!IsValidCellHandle(c_handle, &tst)) {
228 goto fail_vos_BackupVolumeCreate;
232 * Get the volume information and verify that we've been passed
233 * a read write volume id
236 if (!GetVolumeInfo(c_handle, volumeId, &rw_vol_entry, &rw_server,
237 &rw_partition, &rw_vol_type, &tst)) {
238 goto fail_vos_BackupVolumeCreate;
241 if (rw_vol_type != RWVOL) {
242 tst = ADMVOSMUSTBERWVOL;
243 goto fail_vos_BackupVolumeCreate;
247 * Check to see that if a backup volume exists, it exists on the
248 * same server as volumeId
251 if (rw_vol_entry.flags & BACK_EXISTS) {
252 if (!GetVolumeInfo(c_handle, rw_vol_entry.volumeId[BACKVOL],
253 &bk_vol_entry, &bk_server, &bk_partition,
254 &bk_vol_type, &tst)) {
255 goto fail_vos_BackupVolumeCreate;
257 if (!VLDB_IsSameAddrs(c_handle, bk_server, rw_server, &equal, &tst)) {
258 goto fail_vos_BackupVolumeCreate;
261 tst = ADMVOSBACKUPVOLWRONGSERVER;
262 goto fail_vos_BackupVolumeCreate;
267 * Create the new backup volume
270 rc = UV_BackupVolume(c_handle, rw_server, rw_partition, volumeId, &tst);
272 fail_vos_BackupVolumeCreate:
281 * vos_BackupVolumeCreateMultiple - create backup volumes en masse.
285 * IN cellHandle - a previously opened cellHandle that corresponds
286 * to the cell where the volumes exist.
288 * IN serverHandle - the server where the backups are to be created. Can be
291 * IN callBack - a call back function pointer that may be called to report
292 * status information. Can be null.
294 * IN partition - the partition where the backups are to be created. Can be
297 * IN volumePrefix - all volumes with this prefix will have backup volumes
298 * created. Can be null.
300 * IN excludePrefix - exclude the volumes that match volumePrefix.
304 * No locks are obtained or released by this function
308 * Returns != 0 upon successful completion.
311 int ADMINAPI vos_BackupVolumeCreateMultiple(
312 const void *cellHandle,
313 const void *serverHandle,
314 vos_MessageCallBack_t callBack,
315 const unsigned int *partition,
316 const char *volumePrefix,
317 vos_exclude_t excludePrefix,
321 afs_status_t tst = 0;
322 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
323 file_server_p f_server = (file_server_p) serverHandle;
324 struct VldbListByAttributes attr;
327 size_t prefix_len = 0;
328 nbulkentries arrayEntries;
329 afs_int32 nentries = 0;
330 register struct nvldbentry *entry;
332 afs_int32 rw_volid, rw_server, rw_partition;
337 memset((void *) &attr, 0, sizeof(attr));
342 * The only required argument to this function is the cellHandle.
343 * If the excludePrefix is set to VOS_EXCLUDE, volumePrefix must
347 if (!IsValidCellHandle(c_handle, &tst)) {
348 goto fail_vos_BackupVolumeCreateMultiple;
351 if ((excludePrefix == VOS_EXCLUDE) &&
352 ((volumePrefix == NULL) || (*volumePrefix == 0))) {
353 tst = ADMVOSEXCLUDEREQUIRESPREFIX;
354 goto fail_vos_BackupVolumeCreateMultiple;
357 if (f_server != NULL) {
358 if (!IsValidServerHandle(f_server, &tst)) {
359 goto fail_vos_BackupVolumeCreateMultiple;
361 attr.server = ntohl(rx_HostOf(rx_PeerOf(f_server->serv)));
362 attr.Mask |= VLLIST_SERVER;
365 if (partition != NULL) {
366 if (*partition > VOLMAXPARTS) {
367 tst = ADMVOSPARTITIONTOOLARGE;
368 goto fail_vos_BackupVolumeCreateMultiple;
370 attr.partition = *partition;
371 attr.Mask |= VLLIST_PARTITION;
374 if (excludePrefix == VOS_EXCLUDE) {
378 if ((volumePrefix != NULL) && (*volumePrefix != 0)) {
380 prefix_len = strlen(volumePrefix);
383 memset((void *) &arrayEntries, 0, sizeof(arrayEntries));
386 * Get a list of all the volumes in the cell
389 if (!VLDB_ListAttributes(c_handle, &attr, &nentries, &arrayEntries, &tst)) {
390 goto fail_vos_BackupVolumeCreateMultiple;
394 * Cycle through the list of volumes and see if we should create a backup
395 * for each individual volume
398 for(i=0;i<nentries;i++) {
399 entry = &arrayEntries.nbulkentries_val[i];
402 * Skip entries that don't have a RW volume
405 if (!(entry->flags & RW_EXISTS)) {
406 if (callBack != NULL) {
407 const char *messageText;
408 if (util_AdminErrorCodeTranslate(ADMVOSVOLUMENOREADWRITE, 0,
409 &messageText, &tst)) {
410 sprintf(backbuf, "%s %s", messageText, entry->name);
411 (**callBack)(VOS_VERBOSE_MESSAGE, backbuf);
418 * See if we should skip this entry because of the prefix/exclude
419 * combination we've been passed
424 if (!strncmp(entry->name, volumePrefix, prefix_len)) {
428 if (strncmp(entry->name, volumePrefix, prefix_len)) {
434 rw_volid = entry->volumeId[RWVOL];
435 GetServerAndPart(entry, RWVOL, &rw_server, &rw_partition, &previdx);
437 if ((rw_server == -1) || (rw_partition == -1)) {
438 if (callBack != NULL) {
439 const char *messageText;
440 if (util_AdminErrorCodeTranslate(ADMVOSVLDBBADENTRY, 0,
441 &messageText, &tst)) {
442 sprintf(backbuf, "%s %s", messageText, entry->name);
443 (**callBack)(VOS_ERROR_MESSAGE, backbuf);
450 * Check that the RW volume is on the same server that we were
454 if (serverHandle != NULL) {
455 if (!VLDB_IsSameAddrs(c_handle,
456 ntohl(rx_HostOf(rx_PeerOf(f_server->serv))),
457 rw_server, &equal, &tst)) {
458 if (callBack != NULL) {
459 const char *messageText;
460 if (util_AdminErrorCodeTranslate(ADMVOSVLDBBADSERVER, 0,
461 &messageText, &tst)) {
462 sprintf(backbuf, "%s %x %d", messageText,
463 ntohl(rx_HostOf(rx_PeerOf(f_server->serv))),
465 (**callBack)(VOS_ERROR_MESSAGE, backbuf);
471 if (callBack != NULL) {
472 const char *messageText;
473 if (util_AdminErrorCodeTranslate(ADMVOSVLDBDIFFERENTADDR, 0,
474 &messageText, &tst)) {
475 sprintf(backbuf, "%s %s", messageText,
477 (**callBack)(VOS_ERROR_MESSAGE, backbuf);
485 * Check that the RW volume is on the same partition we were
489 if (partition != NULL) {
490 if (*partition != rw_partition) {
499 rc = UV_BackupVolume(c_handle, rw_server, rw_partition, rw_volid, &tst);
502 fail_vos_BackupVolumeCreateMultiple:
504 if (arrayEntries.nbulkentries_val) {
505 free(arrayEntries.nbulkentries_val);
515 * vos_PartitionGet - get information about a single partition.
519 * IN cellHandle - a previously opened cellHandle that corresponds
520 * to the cell where the server lives.
522 * IN serverHandle - a previously open vos server handle that holds
523 * the partition of interest.
525 * IN callBack - a call back function pointer that may be called to report
526 * status information. Can be null.
528 * IN partition - the integer that represents the partition of interest.
530 * OUT partitionP - a pointer to a vos_partitionEntry_t that upon successful
531 * completion contains information regarding the partition.
535 * No locks are obtained or released by this function
539 * Returns != 0 upon successful completion.
542 int ADMINAPI vos_PartitionGet(
543 const void *cellHandle,
544 const void *serverHandle,
545 vos_MessageCallBack_t callBack,
546 unsigned int partition,
547 vos_partitionEntry_p partitionP,
551 afs_status_t tst = 0;
552 struct diskPartition part_info;
553 file_server_p f_server = (file_server_p) serverHandle;
554 char partitionName[10]; /* this rpc requires a character partition name */
560 if (!IsValidServerHandle(f_server, &tst)) {
561 goto fail_vos_PartitionGet;
564 if (partitionP == NULL) {
565 tst = ADMVOSPARTITIONPNULL;
566 goto fail_vos_PartitionGet;
569 if (!vos_PartitionIdToName(partition, partitionName, &tst)) {
570 goto fail_vos_PartitionGet;
573 tst = AFSVolPartitionInfo(f_server->serv, partitionName, &part_info);
575 goto fail_vos_PartitionGet;
577 strcpy(partitionP->name, part_info.name);
578 strcpy(partitionP->deviceName, part_info.devName);
579 partitionP->lockFileDescriptor = part_info.lock_fd;
580 partitionP->totalSpace = part_info.minFree;
581 partitionP->totalFreeSpace = part_info.free;
584 fail_vos_PartitionGet:
593 * The iterator functions and data for the partition retrieval functions.
596 typedef struct partition_get {
597 afs_int32 total_received; /* the total number of valid partiions retrieved */
598 int number_processed; /* the number of valid paritions we've handed out */
599 int index; /* the current index into the part_list array */
600 struct partList part_list; /* the list of partitions */
601 vos_partitionEntry_t partition[CACHED_ITEMS]; /* the cache of partitions */
602 const void *server; /* the server where the parititions exist */
603 } partition_get_t, *partition_get_p;
605 static int GetPartitionInfoRPC(
609 int *last_item_contains_data,
613 afs_status_t tst = 0;
614 partition_get_p part = (partition_get_p) rpc_specific;
615 vos_partitionEntry_p ptr = (vos_partitionEntry_p) &part->partition[slot];
618 * Skip partition entries that are not valid
621 while (!(part->part_list.partFlags[part->index] & PARTVALID)) {
626 * Get information for the next partition
629 if (!vos_PartitionGet(0, part->server, 0,
630 (unsigned int) part->part_list.partId[part->index],
632 goto fail_GetPartitionInfoRPC;
636 part->number_processed++;
638 if (part->number_processed == part->total_received) {
640 *last_item_contains_data = 1;
644 fail_GetPartitionInfoRPC:
652 static int GetPartitionInfoFromCache(
659 afs_status_t tst = 0;
660 partition_get_p part = (partition_get_p) rpc_specific;
662 memcpy(dest, (const void *) &part->partition[slot],
663 sizeof(vos_partitionEntry_t));
673 * vos_PartitionGetBegin - begin to iterate over the partitions at a
678 * IN cellHandle - a previously opened cellHandle that corresponds
679 * to the cell where the server exists.
681 * IN serverHandle - the server that houses the partitions of interest.
683 * IN callBack - a call back function pointer that may be called to report
684 * status information. Can be null.
686 * OUT iterationIdP - upon successful completion, contains an iterator that can
687 * be passed to vos_PartitionGetNext.
691 * No locks are obtained or released by this function
695 * Returns != 0 upon successful completion.
698 int ADMINAPI vos_PartitionGetBegin(
699 const void *cellHandle,
700 const void *serverHandle,
701 vos_MessageCallBack_t callBack,
706 afs_status_t tst = 0;
707 file_server_p f_server = (file_server_p) serverHandle;
708 afs_admin_iterator_p iter = (afs_admin_iterator_p) malloc(sizeof(afs_admin_iterator_t));
709 partition_get_p part = (partition_get_p) calloc(1, sizeof(partition_get_t));
715 if (!IsValidServerHandle(f_server, &tst)) {
716 goto fail_vos_PartitionGetBegin;
719 if (iterationIdP == NULL) {
720 goto fail_vos_PartitionGetBegin;
723 if ((iter == NULL) || (part == NULL)) {
725 goto fail_vos_PartitionGetBegin;
729 * Fill in the part structure
732 part->server = serverHandle;
733 if (!UV_ListPartitions(f_server->serv, &part->part_list,
734 &part->total_received, &tst)) {
735 goto fail_vos_PartitionGetBegin;
739 * If we didn't receive any partitions, don't spawn a background thread.
740 * Mark the iterator complete.
743 if (part->total_received == 0) {
744 if (!IteratorInit(iter, (void *) part, NULL, NULL, NULL, NULL, &tst)) {
745 goto fail_vos_PartitionGetBegin;
747 iter->done_iterating = 1;
748 iter->st = ADMITERATORDONE;
750 if (!IteratorInit(iter, (void *) part, GetPartitionInfoRPC,
751 GetPartitionInfoFromCache, NULL, NULL, &tst)) {
752 goto fail_vos_PartitionGetBegin;
755 *iterationIdP = (void *) iter;
758 fail_vos_PartitionGetBegin:
776 * vos_PartitionGetNext - get the next partition at a server.
780 * IN iterationId - an iterator previously returned by vos_PartitionGetBegin
782 * OUT partitionP - a pointer to a vos_partitionEntry_t that upon successful
783 * completion contains the next partition.
787 * The iterator is locked while the next parition is retrieved.
791 * Returns != 0 upon successful completion.
794 int ADMINAPI vos_PartitionGetNext(
795 const void *iterationId,
796 vos_partitionEntry_p partitionP,
800 afs_status_t tst = 0;
801 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
804 tst = ADMITERATORNULL;
805 goto fail_vos_PartitionGetNext;
808 if (partitionP == NULL) {
809 tst = ADMVOSPARTITIONPNULL;
810 goto fail_vos_PartitionGetNext;
813 rc = IteratorNext(iter, (void *) partitionP, &tst);
815 fail_vos_PartitionGetNext:
824 * vos_PartitionGetDone - finish using a partition iterator.
828 * IN iterationId - an iterator previously returned by vos_PartitionGetBegin
832 * The iterator is locked and then destroyed.
836 * Returns != 0 upon successful completion.
839 int ADMINAPI vos_PartitionGetDone(
840 const void *iterationId,
844 afs_status_t tst = 0;
845 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
852 tst = ADMITERATORNULL;
853 goto fail_vos_PartitionGetDone;
856 rc = IteratorDone(iter, &tst);
858 fail_vos_PartitionGetDone:
867 * vos_ServerOpen - open a handle to an individual server for future
872 * IN cellHandle - a previously opened cellHandle that corresponds
873 * to the cell where the server lives.
875 * IN serverName - the machine name of the server
877 * OUT serverHandleP - a void pointer that upon successful completion
878 * contains a handle that is used in future operations upon the server.
882 * No locks are obtained or released by this function
886 * Returns != 0 upon successful completion.
889 int ADMINAPI vos_ServerOpen(
890 const void *cellHandle,
891 const char *serverName,
892 void **serverHandleP,
896 afs_status_t tst = 0;
897 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
898 file_server_p f_server = (file_server_p) malloc(sizeof(file_server_t));
900 struct rx_securityClass *sc[3];
903 if (f_server == NULL) {
905 goto fail_vos_ServerOpen;
912 if (!IsValidCellHandle(c_handle, &tst)) {
913 goto fail_vos_ServerOpen;
916 if (!c_handle->tokens->afs_token_set) {
917 tst = ADMVOSCELLHANDLENOAFSTOKENS;
918 goto fail_vos_ServerOpen;
921 if (!util_AdminServerAddressGetFromName(serverName, &server_address,
923 goto fail_vos_ServerOpen;
926 scIndex = c_handle->tokens->sc_index;
927 sc[scIndex] = c_handle->tokens->afs_sc[scIndex];
928 f_server->serv = rx_GetCachedConnection(htonl(server_address),
929 htons(AFSCONF_VOLUMEPORT),
930 VOLSERVICE_ID, sc[scIndex], scIndex);
931 if (f_server->serv != NULL) {
932 f_server->begin_magic = BEGIN_MAGIC;
933 f_server->end_magic = END_MAGIC;
934 f_server->is_valid = 1;
935 *serverHandleP = (void *) f_server;
938 tst = ADMVOSSERVERNOCONNECTION;
939 goto fail_vos_ServerOpen;
951 * vos_ServerClose - close a handle previously obtained from vos_ServerOpen
955 * IN serverHandle - an existing server handle.
959 * No locks are obtained or released by this function
963 * Returns != 0 upon successful completion.
966 int ADMINAPI vos_ServerClose(
967 const void *serverHandle,
971 afs_status_t tst = 0;
972 file_server_p f_server = (file_server_p) serverHandle;
974 if (!IsValidServerHandle(f_server, &tst)) {
975 goto fail_vos_ServerClose;
978 rx_ReleaseCachedConnection(f_server->serv);
979 f_server->is_valid = 0;
983 fail_vos_ServerClose:
992 * vos_ServerSync - synchronize the vldb and the fileserver at a particular
997 * IN cellHandle - a previously opened cellHandle that corresponds
998 * to the cell where the server lives.
1000 * IN serverHandle - a handle to the server machine.
1002 * IN callBack - a call back function pointer that may be called to report
1003 * status information. Can be null.
1005 * IN partition - the partition to synchronize. Can be NULL.
1007 * IN force - force deletion of bad volumes.
1011 * No locks are obtained or released by this function
1015 * Returns != 0 upon successful completion.
1018 int ADMINAPI vos_ServerSync(
1019 const void *cellHandle,
1020 const void *serverHandle,
1021 vos_MessageCallBack_t callBack,
1022 const unsigned int *partition,
1026 afs_status_t tst = 0;
1027 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
1028 file_server_p f_server = (file_server_p) serverHandle;
1033 * Validate arguments
1036 if (!IsValidCellHandle(c_handle, &tst)) {
1037 goto fail_vos_ServerSync;
1040 if (!IsValidServerHandle(f_server, &tst)) {
1041 goto fail_vos_ServerSync;
1044 if (partition != NULL) {
1045 if (*partition > VOLMAXPARTS) {
1046 tst = ADMVOSPARTITIONTOOLARGE;
1047 goto fail_vos_ServerSync;
1049 part = (afs_int32) *partition;
1057 rc = UV_SyncServer(c_handle, f_server->serv, part, flags, &tst);
1059 fail_vos_ServerSync:
1068 * vos_FileServerAddressChange - change an existing file server address.
1072 * IN cellHandle - a previously opened cellHandle that corresponds
1073 * to the cell where the address should be changed.
1075 * IN callBack - a call back function pointer that may be called to report
1076 * status information. Can be null.
1078 * IN oldAddress - the old server address in host byte order
1080 * IN newAddress - the new server address in host byte order
1084 * No locks are obtained or released by this function
1088 * Returns != 0 upon successful completion.
1091 int ADMINAPI vos_FileServerAddressChange(
1092 const void *cellHandle,
1093 vos_MessageCallBack_t callBack,
1099 afs_status_t tst = 0;
1100 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
1103 * Validate arguments
1106 if (!IsValidCellHandle(c_handle, &tst)) {
1107 goto fail_vos_FileServerAddressChange;
1110 tst = ubik_Call_New(VL_ChangeAddr, c_handle->vos, 0,
1111 oldAddress, newAddress);
1113 goto fail_vos_FileServerAddressChange;
1117 fail_vos_FileServerAddressChange:
1126 * vos_FileServerAddressRemove - remove an existing file server address.
1130 * IN cellHandle - a previously opened cellHandle that corresponds
1131 * to the cell where the address should be removed.
1133 * IN callBack - a call back function pointer that may be called to report
1134 * status information. Can be null.
1136 * IN serverAddress - the server address to remove in host byte order.
1140 * No locks are obtained or released by this function
1144 * Returns != 0 upon successful completion.
1147 int ADMINAPI vos_FileServerAddressRemove(
1148 const void *cellHandle,
1149 vos_MessageCallBack_t callBack,
1154 afs_status_t tst = 0;
1155 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
1156 int dummyAddress = 0xffffffff;
1159 * Validate arguments
1162 if (!IsValidCellHandle(c_handle, &tst)) {
1163 goto fail_vos_FileServerAddressRemove;
1166 tst = ubik_Call_New(VL_ChangeAddr, c_handle->vos, 0,
1167 dummyAddress, serverAddress);
1169 goto fail_vos_FileServerAddressRemove;
1173 fail_vos_FileServerAddressRemove:
1182 * The iterator functions and data for the server retrieval functions.
1184 * These functions are very similar to the FileServerAddressGet
1185 * functions. The main difference being that instead of returning
1186 * a single address at a time for a server, we fill an array with
1187 * all the addresses of a server.
1190 typedef struct server_get {
1191 struct ubik_client *vldb; /* connection for future rpc's if neccessary */
1192 afs_int32 total_addresses; /* total number of addresses */
1193 bulkaddrs addresses; /* the list of addresses */
1194 int address_index; /* current index into address list */
1195 vos_fileServerEntry_t server[CACHED_ITEMS]; /* the cache of servers */
1196 } server_get_t, *server_get_p;
1198 static int GetServerRPC(
1202 int *last_item_contains_data,
1206 afs_status_t tst = 0;
1207 server_get_p serv = (server_get_p) rpc_specific;
1208 afs_uint32 *addrP = &serv->addresses.bulkaddrs_val[serv->address_index];
1209 afs_int32 base, index;
1212 ListAddrByAttributes m_attrs;
1213 afs_int32 total_multi;
1214 bulkaddrs addr_multi;
1218 * Check to see if this is a multihomed address server
1221 if ( ((*addrP & 0xff000000) == 0xff000000) && ((*addrP)&0xffff) ) {
1222 base = (*addrP>>16) & 0xff;
1223 index = (*addrP) & 0xffff;
1225 if ((base >= 0) && (base <= VL_MAX_ADDREXTBLKS) &&
1226 (index >= 1) && (index <= VL_MHSRV_PERBLK)) {
1229 * This is a multihomed server. Make an rpc to retrieve
1230 * all its addresses. Copy the addresses into the cache.
1233 m_attrs.Mask = VLADDR_INDEX;
1234 m_attrs.index = (base * VL_MHSRV_PERBLK) + index;
1236 addr_multi.bulkaddrs_val = 0;
1237 addr_multi.bulkaddrs_len = 0;
1238 tst = ubik_Call(VL_GetAddrsU, serv->vldb, 0, &m_attrs, &m_uuid,
1243 goto fail_GetServerRPC;
1247 * Remove any bogus IP addresses which the user may have
1248 * been unable to remove.
1251 RemoveBadAddresses (&total_multi, &addr_multi);
1254 * Copy all the addresses into the cache
1257 for(i=0;i<total_multi;i++) {
1258 serv->server[slot].serverAddress[i] =
1259 addr_multi.bulkaddrs_val[i];
1262 serv->server[slot].count = total_multi;
1263 serv->address_index++;
1264 free(addr_multi.bulkaddrs_val);
1268 * The next address is just a plain old address
1272 serv->server[slot].serverAddress[0] = *addrP;
1273 serv->server[slot].count = 1;
1274 serv->address_index++;
1278 * See if we've processed all the entries
1282 if (serv->address_index == serv->total_addresses) {
1284 *last_item_contains_data = 1;
1296 static int GetServerFromCache(
1303 afs_status_t tst = 0;
1304 server_get_p serv = (server_get_p) rpc_specific;
1306 memcpy(dest, (const void *) &serv->server[slot],
1307 sizeof(vos_fileServerEntry_t));
1317 static int DestroyServer(
1322 afs_status_t tst = 0;
1323 server_get_p serv = (server_get_p) rpc_specific;
1325 if (serv->addresses.bulkaddrs_val != NULL) {
1326 free(serv->addresses.bulkaddrs_val);
1337 * vos_FileServerGetBegin - begin to iterate over the file servers in a cell.
1341 * IN cellHandle - a previously opened cellHandle that corresponds
1342 * to the cell where the file servers exist.
1344 * IN callBack - a call back function pointer that may be called to report
1345 * status information. Can be null.
1347 * OUT iterationIdP - upon successful completion, contains an iterator that
1348 * can be passed to vos_FileServerGetNext.
1352 * No locks are obtained or released by this function
1356 * Returns != 0 upon successful completion.
1359 int ADMINAPI vos_FileServerGetBegin(
1360 const void *cellHandle,
1361 vos_MessageCallBack_t callBack,
1362 void **iterationIdP,
1366 afs_status_t tst = 0;
1367 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
1368 afs_admin_iterator_p iter = (afs_admin_iterator_p) malloc(sizeof(afs_admin_iterator_t));
1369 server_get_p serv = (server_get_p) calloc(1, sizeof(server_get_t));
1370 struct VLCallBack unused;
1374 * Validate arguments
1377 if (!IsValidCellHandle(c_handle, &tst)) {
1378 goto fail_vos_FileServerGetBegin;
1381 if (iterationIdP == NULL) {
1382 goto fail_vos_FileServerGetBegin;
1385 if ((iter == NULL) || (serv == NULL)) {
1387 goto fail_vos_FileServerGetBegin;
1391 * Fill in the serv structure
1394 serv->vldb = c_handle->vos;
1395 tst = ubik_Call_New(VL_GetAddrs, c_handle->vos, 0, 0, 0, &unused,
1396 &serv->total_addresses, &serv->addresses);
1399 goto fail_vos_FileServerGetBegin;
1403 * Remove any bogus IP addresses which the user may have
1404 * been unable to remove.
1407 RemoveBadAddresses (&serv->total_addresses, &serv->addresses);
1409 if (serv->total_addresses == 0) {
1410 if (!IteratorInit(iter, (void *) serv, NULL, NULL, NULL, NULL, &tst)) {
1411 goto fail_vos_FileServerGetBegin;
1413 iter->done_iterating = 1;
1414 iter->st = ADMITERATORDONE;
1416 if (!IteratorInit(iter, (void *) serv, GetServerRPC,
1417 GetServerFromCache, NULL, DestroyServer, &tst)) {
1418 goto fail_vos_FileServerGetBegin;
1421 *iterationIdP = (void *) iter;
1424 fail_vos_FileServerGetBegin:
1431 if (serv->addresses.bulkaddrs_val != NULL) {
1432 free(serv->addresses.bulkaddrs_val);
1445 * vos_FileServerGetNext - get information about the next fileserver in the cell.
1449 * IN iterationId - an iterator previously returned by
1450 * vos_FileServerGetBegin
1452 * OUT serverEntryP - a pointer to a vos_fileServerEntry_t that upon successful
1453 * completion contains information about the next server in the cell.
1457 * The iterator is locked while the next server is retrieved.
1461 * Returns != 0 upon successful completion.
1464 int ADMINAPI vos_FileServerGetNext(
1466 vos_fileServerEntry_p serverEntryP,
1470 afs_status_t tst = 0;
1471 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1474 tst = ADMITERATORNULL;
1475 goto fail_vos_FileServerGetNext;
1478 if (serverEntryP == NULL) {
1479 tst = ADMVOSSERVERENTRYPNULL;
1480 goto fail_vos_FileServerGetNext;
1483 rc = IteratorNext(iter, (void *) serverEntryP, &tst);
1485 fail_vos_FileServerGetNext:
1494 * vos_FileServerGetDone - finish using a partition iterator.
1498 * IN iterationId - an iterator previously returned by vos_FileServerGetBegin
1502 * The iterator is locked and then destroyed.
1506 * Returns != 0 upon successful completion.
1509 int ADMINAPI vos_FileServerGetDone(
1514 afs_status_t tst = 0;
1515 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1518 * Validate arguments
1522 tst = ADMITERATORNULL;
1523 goto fail_vos_FileServerGetDone;
1526 rc = IteratorDone(iter, &tst);
1528 fail_vos_FileServerGetDone:
1537 * The iterator functions and data for the transation retrieval functions.
1540 typedef struct transaction_get {
1541 afs_int32 total; /* total number of transactions */
1542 afs_int32 index; /* index to the current transaction */
1543 transDebugInfo *cur; /* the current transaction */
1544 vos_serverTransactionStatus_t tran[CACHED_ITEMS]; /* the cache of trans */
1545 } transaction_get_t, *transaction_get_p;
1547 static int GetTransactionRPC(
1551 int *last_item_contains_data,
1555 afs_status_t tst = 0;
1556 transaction_get_p t = (transaction_get_p) rpc_specific;
1557 int index = t->index;
1560 * Copy the next transaction into the cache
1563 t->tran[slot].transactionId = t->cur[index].tid;
1564 t->tran[slot].lastActiveTime = t->cur[index].time;
1565 t->tran[slot].creationTime = t->cur[index].creationTime;
1566 t->tran[slot].errorCode = t->cur[index].returnCode;
1567 t->tran[slot].volumeId = t->cur[index].volid;
1568 t->tran[slot].partition = t->cur[index].partition;
1569 strcpy(t->tran[slot].lastProcedureName, t->cur[index].lastProcName);
1570 t->tran[slot].nextReceivePacketSequenceNumber = t->cur[index].readNext;
1571 t->tran[slot].nextSendPacketSequenceNumber = t->cur[index].transmitNext;
1572 t->tran[slot].lastReceiveTime = t->cur[index].lastReceiveTime;
1573 t->tran[slot].lastSendTime = t->cur[index].lastSendTime;
1575 t->tran[slot].volumeAttachMode = VOS_VOLUME_ATTACH_MODE_OK;
1577 switch(t->cur[index].iflags){
1579 t->tran[slot].volumeAttachMode = VOS_VOLUME_ATTACH_MODE_OFFLINE;
1582 t->tran[slot].volumeAttachMode = VOS_VOLUME_ATTACH_MODE_BUSY;
1585 t->tran[slot].volumeAttachMode = VOS_VOLUME_ATTACH_MODE_READONLY;
1588 t->tran[slot].volumeAttachMode = VOS_VOLUME_ATTACH_MODE_CREATE;
1591 t->tran[slot].volumeAttachMode = VOS_VOLUME_ATTACH_MODE_CREATE_VOLID;
1595 t->tran[slot].volumeActiveStatus = VOS_VOLUME_ACTIVE_STATUS_OK;
1597 switch(t->cur[index].vflags){
1598 case VTDeleteOnSalvage:
1599 t->tran[slot].volumeActiveStatus =
1600 VOS_VOLUME_ACTIVE_STATUS_DELETE_ON_SALVAGE;
1602 case VTOutOfService:
1603 t->tran[slot].volumeActiveStatus =
1604 VOS_VOLUME_ACTIVE_STATUS_OUT_OF_SERVICE;
1607 t->tran[slot].volumeActiveStatus =
1608 VOS_VOLUME_ACTIVE_STATUS_DELETED;
1612 t->tran[slot].volumeTransactionStatus = VOS_VOLUME_TRANSACTION_STATUS_OK;
1614 if (t->cur[index].tflags) {
1615 t->tran[slot].volumeTransactionStatus =
1616 VOS_VOLUME_TRANSACTION_STATUS_DELETED;
1622 * See if we've processed all the entries
1626 if (t->index == t->total) {
1628 *last_item_contains_data = 1;
1638 static int GetTransactionFromCache(
1645 afs_status_t tst = 0;
1646 transaction_get_p tran = (transaction_get_p) rpc_specific;
1648 memcpy(dest, (const void *) &tran->tran[slot],
1649 sizeof(vos_serverTransactionStatus_p));
1659 static int DestroyTransaction(
1664 afs_status_t tst = 0;
1665 transaction_get_p tran = (transaction_get_p) rpc_specific;
1667 if (tran->cur != NULL) {
1679 * vos_ServerTransactionStatusGetBegin - begin to iterate over the transactions
1680 * at a volume server.
1684 * IN cellHandle - a previously opened cellHandle that corresponds
1685 * to the cell where the volume server exists.
1687 * IN serverHandle - a handle to the server to query.
1689 * IN callBack - a call back function pointer that may be called to report
1690 * status information. Can be null.
1692 * OUT iterationIdP - upon successful completion, contains an iterator that
1693 * can be passed to vos_ServerTransactionStatusGetNext.
1697 * No locks are obtained or released by this function
1701 * Returns != 0 upon successful completion.
1704 int ADMINAPI vos_ServerTransactionStatusGetBegin(
1705 const void *cellHandle,
1706 const void *serverHandle,
1707 vos_MessageCallBack_t callBack,
1708 void **iterationIdP,
1712 afs_status_t tst = 0;
1713 file_server_p f_server = (file_server_p) serverHandle;
1714 afs_admin_iterator_p iter = (afs_admin_iterator_p) malloc(sizeof(afs_admin_iterator_t));
1715 transaction_get_p tran = (transaction_get_p) calloc(1, sizeof(transaction_get_t));
1719 * Validate arguments
1722 if (!IsValidServerHandle(f_server, &tst)) {
1723 goto fail_vos_ServerTransactionStatusGetBegin;
1726 if (iterationIdP == NULL) {
1727 goto fail_vos_ServerTransactionStatusGetBegin;
1730 if ((iter == NULL) || (tran == NULL)) {
1732 goto fail_vos_ServerTransactionStatusGetBegin;
1736 * Fill in the tran structure
1739 if (!UV_VolserStatus(f_server->serv, &tran->cur, &tran->total, &tst)) {
1740 goto fail_vos_ServerTransactionStatusGetBegin;
1743 if (tran->total == 0) {
1744 if (!IteratorInit(iter, (void *) tran, NULL,
1745 NULL, NULL, NULL, &tst)) {
1746 goto fail_vos_ServerTransactionStatusGetBegin;
1748 iter->done_iterating = 1;
1749 iter->st = ADMITERATORDONE;
1751 if (!IteratorInit(iter, (void *) tran, GetTransactionRPC,
1752 GetTransactionFromCache, NULL,
1753 DestroyTransaction, &tst)) {
1754 goto fail_vos_ServerTransactionStatusGetBegin;
1757 *iterationIdP = (void *) iter;
1760 fail_vos_ServerTransactionStatusGetBegin:
1767 if (tran->cur != NULL) {
1781 * vos_ServerTransactionStatusGetNext - get information about the next
1782 * active transaction.
1786 * IN iterationId - an iterator previously returned by
1787 * vos_ServerTransactionStatusGetBegin
1789 * OUT serverTransactionStatusP - a pointer to a vos_serverTransactionStatus_p
1790 * that upon successful completion contains information about the
1795 * The iterator is locked while the next item is retrieved.
1799 * Returns != 0 upon successful completion.
1802 int ADMINAPI vos_ServerTransactionStatusGetNext(
1803 const void *iterationId,
1804 vos_serverTransactionStatus_p serverTransactionStatusP,
1808 afs_status_t tst = 0;
1809 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1812 tst = ADMITERATORNULL;
1813 goto fail_vos_ServerTransactionStatusGetNext;
1816 if (serverTransactionStatusP == NULL) {
1817 tst = ADMVOSSERVERTRANSACTIONSTATUSPNULL;
1818 goto fail_vos_ServerTransactionStatusGetNext;
1821 rc = IteratorNext(iter, (void *) serverTransactionStatusP, &tst);
1823 fail_vos_ServerTransactionStatusGetNext:
1832 * vos_ServerTransactionStatusGetDone - finish using a transaction iterator.
1836 * IN iterationId - an iterator previously returned by
1837 * vos_ServerTransactionStatusGetBegin
1841 * The iterator is locked and then destroyed.
1845 * Returns != 0 upon successful completion.
1848 int ADMINAPI vos_ServerTransactionStatusGetDone(
1849 const void *iterationId,
1853 afs_status_t tst = 0;
1854 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
1857 * Validate arguments
1861 tst = ADMITERATORNULL;
1862 goto fail_vos_ServerTransactionStatusGetDone;
1865 rc = IteratorDone(iter, &tst);
1867 fail_vos_ServerTransactionStatusGetDone:
1875 static int copyVLDBEntry(
1876 struct nvldbentry *source,
1877 vos_vldbEntry_p dest,
1881 afs_status_t tst = 0;
1884 dest->numServers = source->nServers;
1885 for (i=0;i<VOS_MAX_VOLUME_TYPES;i++) {
1886 dest->volumeId[i] = source->volumeId[i];
1888 dest->cloneId = source->cloneId;
1889 dest->status = VOS_VLDB_ENTRY_OK;
1890 if (source->flags & VLOP_ALLOPERS) {
1891 dest->status |= VOS_VLDB_ENTRY_LOCKED;
1894 if (source->flags & VLOP_MOVE) {
1895 dest->status |= VOS_VLDB_ENTRY_MOVE;
1897 if (source->flags & VLOP_RELEASE) {
1898 dest->status |= VOS_VLDB_ENTRY_RELEASE;
1900 if (source->flags & VLOP_BACKUP) {
1901 dest->status |= VOS_VLDB_ENTRY_BACKUP;
1903 if (source->flags & VLOP_DELETE) {
1904 dest->status |= VOS_VLDB_ENTRY_DELETE;
1906 if (source->flags & VLOP_DUMP) {
1907 dest->status |= VOS_VLDB_ENTRY_DUMP;
1910 if (source->flags & VLF_RWEXISTS) {
1911 dest->status |= VOS_VLDB_ENTRY_RWEXISTS;
1913 if (source->flags & VLF_ROEXISTS) {
1914 dest->status |= VOS_VLDB_ENTRY_ROEXISTS;
1916 if (source->flags & VLF_BACKEXISTS) {
1917 dest->status |= VOS_VLDB_ENTRY_BACKEXISTS;
1920 strcpy(dest->name, source->name);
1921 for (i=0;i<VOS_MAX_REPLICA_SITES;i++) {
1922 dest->volumeSites[i].serverAddress = source->serverNumber[i];
1923 dest->volumeSites[i].serverPartition = source->serverPartition[i];
1924 dest->volumeSites[i].serverFlags = 0;
1926 if (source->serverFlags[i] & NEW_REPSITE) {
1927 dest->volumeSites[i].serverFlags |= VOS_VLDB_NEW_REPSITE;
1929 if (source->serverFlags[i] & ITSROVOL) {
1930 dest->volumeSites[i].serverFlags |= VOS_VLDB_READ_ONLY;
1932 if (source->serverFlags[i] & ITSRWVOL) {
1933 dest->volumeSites[i].serverFlags |= VOS_VLDB_READ_WRITE;
1935 if (source->serverFlags[i] & ITSBACKVOL) {
1936 dest->volumeSites[i].serverFlags |= VOS_VLDB_BACKUP;
1938 if (source->serverFlags[i] & RO_DONTUSE) {
1939 dest->volumeSites[i].serverFlags |= VOS_VLDB_DONT_USE;
1952 * vos_VLDBGet- get a volume's vldb entry.
1956 * IN cellHandle - a previously opened cellHandle that corresponds
1957 * to the cell where the volume entries exist.
1959 * IN callBack - a call back function pointer that may be called to report
1960 * status information. Can be null.
1962 * IN volumeId - the id of the volume to retrieve.
1964 * IN volumeName - the name of the volume to retrieve.
1966 * OUT vldbEntry - upon successful completion, contains the information regarding
1971 * No locks are obtained or released by this function
1975 * Returns != 0 upon successful completion.
1978 int ADMINAPI vos_VLDBGet(
1979 const void *cellHandle,
1980 vos_MessageCallBack_t callBack,
1981 const unsigned int *volumeId,
1982 const char *volumeName,
1983 vos_vldbEntry_p vldbEntry,
1987 afs_status_t tst = 0;
1988 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
1989 struct nvldbentry entry;
1993 * Validate arguments
1996 if (!IsValidCellHandle(c_handle, &tst)) {
1997 goto fail_vos_VLDBGet;
2000 if (vldbEntry == NULL) {
2001 tst = ADMVOSVLDBENTRYNULL;
2002 goto fail_vos_VLDBGet;
2005 if (((volumeName == NULL) || (*volumeName == 0)) &&
2006 (volumeId == NULL)) {
2007 tst = ADMVOSVOLUMENAMEANDVOLUMEIDNULL;
2008 goto fail_vos_VLDBGet;
2012 * Retrieve the entry
2015 if (!((volumeName == NULL) || (*volumeName == 0))) {
2016 if (!ValidateVolumeName(volumeName, &tst)) {
2017 goto fail_vos_VLDBGet;
2019 if (!VLDB_GetEntryByName(c_handle, volumeName, &entry, &tst)) {
2020 goto fail_vos_VLDBGet;
2023 if (!VLDB_GetEntryByID(c_handle, *volumeId, -1, &entry, &tst)) {
2024 goto fail_vos_VLDBGet;
2029 * Copy the entry into our structure
2032 if (!copyVLDBEntry(&entry, vldbEntry, &tst)) {
2033 goto fail_vos_VLDBGet;
2046 * The iterator functions and data for the vldb entry retrieval functions.
2049 typedef struct vldb_entry_get {
2050 afs_int32 total; /* total number of vldb entries */
2051 afs_int32 index; /* index to the current vldb entry */
2052 nbulkentries entries; /* the list of entries retrieved */
2053 vos_vldbEntry_t entry[CACHED_ITEMS]; /* the cache of entries */
2054 } vldb_entry_get_t, *vldb_entry_get_p;
2056 static int GetVLDBEntryRPC(
2060 int *last_item_contains_data,
2064 afs_status_t tst = 0;
2065 vldb_entry_get_p entry = (vldb_entry_get_p) rpc_specific;
2068 * Copy the next entry into the cache
2071 if (!copyVLDBEntry(&entry->entries.nbulkentries_val[entry->index],
2072 &entry->entry[slot],
2074 goto fail_GetVLDBEntryRPC;
2079 * See if we've processed all the entries
2083 if (entry->index == entry->total) {
2085 *last_item_contains_data = 1;
2089 fail_GetVLDBEntryRPC:
2097 static int GetVLDBEntryFromCache(
2104 afs_status_t tst = 0;
2105 vldb_entry_get_p entry = (vldb_entry_get_p) rpc_specific;
2107 memcpy(dest, (const void *) &entry->entry[slot],
2108 sizeof(vos_vldbEntry_t));
2118 static int DestroyVLDBEntry(
2123 afs_status_t tst = 0;
2124 vldb_entry_get_p entry = (vldb_entry_get_p) rpc_specific;
2126 if (entry->entries.nbulkentries_val != NULL) {
2127 free(entry->entries.nbulkentries_val);
2139 * vos_VLDBGetBegin - begin to iterate over the VLDB.
2143 * IN cellHandle - a previously opened cellHandle that corresponds
2144 * to the cell where the volume entries exist.
2146 * IN serverHandle - a handle to the server whose entries should be listed.
2149 * IN callBack - a call back function pointer that may be called to report
2150 * status information. Can be null.
2152 * IN partition - the partition whose entries should be listed.
2155 * OUT iterationIdP - upon successful completion, contains an iterator that
2156 * can be passed to vos_VLDBGetNext.
2160 * No locks are obtained or released by this function
2164 * Returns != 0 upon successful completion.
2167 int ADMINAPI vos_VLDBGetBegin(
2168 const void *cellHandle,
2169 const void *serverHandle,
2170 vos_MessageCallBack_t callBack,
2171 unsigned int *partition,
2172 void **iterationIdP,
2176 afs_status_t tst = 0;
2177 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2178 file_server_p f_server = (file_server_p) serverHandle;
2179 afs_admin_iterator_p iter = (afs_admin_iterator_p) malloc(sizeof(afs_admin_iterator_t));
2180 vldb_entry_get_p entry = (vldb_entry_get_p) calloc(1, sizeof(vldb_entry_get_t));
2181 struct VldbListByAttributes attr;
2184 memset(&attr, 0, sizeof(attr));
2187 * Validate arguments
2190 if (!IsValidCellHandle(c_handle, &tst)) {
2191 goto fail_vos_VLDBGetBegin;
2194 if ((iter == NULL) || (entry == NULL)) {
2196 goto fail_vos_VLDBGetBegin;
2199 if (f_server != NULL) {
2200 if (!IsValidServerHandle(f_server, &tst)) {
2201 goto fail_vos_VLDBGetBegin;
2203 attr.server = ntohl(rx_HostOf(rx_PeerOf(f_server->serv)));
2204 attr.Mask |= VLLIST_SERVER;
2207 if (partition != NULL) {
2208 if (*partition > VOLMAXPARTS) {
2209 tst = ADMVOSPARTITIONTOOLARGE;
2210 goto fail_vos_VLDBGetBegin;
2212 attr.partition = *partition;
2213 attr.Mask |= VLLIST_PARTITION;
2216 if (!VLDB_ListAttributes(c_handle, &attr, &entry->total, &entry->entries, &tst)) {
2217 goto fail_vos_VLDBGetBegin;
2220 if (entry->total <= 0) {
2221 if (!IteratorInit(iter, (void *) entry, NULL,
2222 NULL, NULL, NULL, &tst)) {
2223 goto fail_vos_VLDBGetBegin;
2225 iter->done_iterating = 1;
2226 iter->st = ADMITERATORDONE;
2228 if (!IteratorInit(iter, (void *) entry, GetVLDBEntryRPC,
2229 GetVLDBEntryFromCache, NULL,
2230 DestroyVLDBEntry, &tst)) {
2231 goto fail_vos_VLDBGetBegin;
2234 *iterationIdP = (void *) iter;
2237 fail_vos_VLDBGetBegin:
2243 if (entry->entries.nbulkentries_val != NULL) {
2244 free(entry->entries.nbulkentries_val);
2246 if (entry != NULL) {
2258 * vos_VLDBGetNext - get information about the next volume.
2262 * IN iterationId - an iterator previously returned by
2265 * OUT vldbEntry - a pointer to a vos_vldbEntry_t
2266 * that upon successful completion contains information about the
2271 * The iterator is locked while the next item is retrieved.
2275 * Returns != 0 upon successful completion.
2278 int ADMINAPI vos_VLDBGetNext(
2279 const void *iterationId,
2280 vos_vldbEntry_p vldbEntry,
2284 afs_status_t tst = 0;
2285 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
2288 tst = ADMITERATORNULL;
2289 goto fail_vos_VLDBGetNext;
2292 if (vldbEntry == NULL) {
2293 tst = ADMVOSVLDBENTRYNULL;
2294 goto fail_vos_VLDBGetNext;
2297 rc = IteratorNext(iter, (void *) vldbEntry, &tst);
2299 fail_vos_VLDBGetNext:
2308 * vos_VLDBGetDone - finish using a volume iterator.
2312 * IN iterationId - an iterator previously returned by vos_VLDBGetBegin
2316 * The iterator is locked and then destroyed.
2320 * Returns != 0 upon successful completion.
2323 int ADMINAPI vos_VLDBGetDone(
2324 const void *iterationId,
2328 afs_status_t tst = 0;
2329 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
2332 * Validate arguments
2336 tst = ADMITERATORNULL;
2337 goto fail_vos_VLDBGetDone;
2340 rc = IteratorDone(iter, &tst);
2342 fail_vos_VLDBGetDone:
2351 * vos_VLDBEntryRemove - remove a vldb entry.
2355 * IN cellHandle - a previously opened cellHandle that corresponds
2356 * to the cell where the vldb entry exists.
2358 * IN serverHandle - a previously opened serverHandle that corresponds
2359 * to the server where the vldb entry exists. Can be null.
2361 * IN callBack - a call back function pointer that may be called to report
2362 * status information. Can be null.
2364 * IN partition - the partition where the vldb entry exists. Can be null.
2366 * IN volumeId - the volume id of the vldb entry to be deleted. Can be null.
2370 * No locks are obtained or released by this function
2374 * Returns != 0 upon successful completion.
2377 int ADMINAPI vos_VLDBEntryRemove(
2378 const void *cellHandle,
2379 const void *serverHandle,
2380 vos_MessageCallBack_t callBack,
2381 const unsigned int *partition,
2382 unsigned int *volumeId,
2386 afs_status_t tst = 0;
2387 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2388 file_server_p f_server = (file_server_p) serverHandle;
2389 struct VldbListByAttributes attr;
2390 nbulkentries entries;
2394 memset(&attr, 0, sizeof(attr));
2395 memset(&entries, 0, sizeof(entries));
2398 * Validate arguments
2401 if (!IsValidCellHandle(c_handle, &tst)) {
2402 goto fail_vos_VLDBEntryRemove;
2406 * If the volume is specified, just delete it
2409 if (volumeId != NULL) {
2410 tst = ubik_Call(VL_DeleteEntry, c_handle->vos, 0, *volumeId, -1);
2412 goto fail_vos_VLDBEntryRemove;
2416 if (f_server != NULL) {
2417 if (!IsValidServerHandle(f_server, &tst)) {
2418 goto fail_vos_VLDBEntryRemove;
2420 attr.server = ntohl(rx_HostOf(rx_PeerOf(f_server->serv)));
2421 attr.Mask |= VLLIST_SERVER;
2424 if (partition != NULL) {
2425 if (*partition > VOLMAXPARTS) {
2426 tst = ADMVOSPARTITIONTOOLARGE;
2427 goto fail_vos_VLDBEntryRemove;
2429 attr.partition = *partition;
2430 attr.Mask |= VLLIST_PARTITION;
2433 if ((f_server == NULL) && (partition == NULL)) {
2434 tst = ADMVOSVLDBDELETEALLNULL;
2435 goto fail_vos_VLDBEntryRemove;
2438 if (!VLDB_ListAttributes(c_handle, &attr, &nentries, &entries, &tst)) {
2439 goto fail_vos_VLDBEntryRemove;
2442 if (nentries <= 0) {
2443 tst = ADMVOSVLDBNOENTRIES;
2444 goto fail_vos_VLDBEntryRemove;
2447 for(i=0;i<nentries;i++) {
2448 ubik_Call(VL_DeleteEntry, c_handle->vos, 0, entries.nbulkentries_val[i].volumeId[RWVOL]);
2452 fail_vos_VLDBEntryRemove:
2454 if (entries.nbulkentries_val) {
2455 free(entries.nbulkentries_val);
2465 * vos_VLDBUnlock - unlock vldb entries en masse.
2469 * IN cellHandle - a previously opened cellHandle that corresponds
2470 * to the cell where the vldb entries exist.
2472 * IN serverHandle - a previously opened serverHandle that corresponds
2473 * to the server where the vldb entries exist. Can be null.
2475 * IN callBack - a call back function pointer that may be called to report
2476 * status information. Can be null.
2478 * IN partition - the partition where the vldb entries exist. Can be null.
2482 * No locks are obtained or released by this function
2486 * Returns != 0 upon successful completion.
2489 int ADMINAPI vos_VLDBUnlock(
2490 const void *cellHandle,
2491 const void *serverHandle,
2492 vos_MessageCallBack_t callBack,
2493 const unsigned int *partition,
2497 afs_status_t tst = 0;
2498 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2499 file_server_p f_server = (file_server_p) serverHandle;
2500 struct VldbListByAttributes attr;
2501 nbulkentries entries;
2505 memset(&attr, 0, sizeof(attr));
2506 memset(&entries, 0, sizeof(entries));
2509 * Validate arguments
2512 if (!IsValidCellHandle(c_handle, &tst)) {
2513 goto fail_vos_VLDBUnlock;
2516 if (f_server != NULL) {
2517 if (!IsValidServerHandle(f_server, &tst)) {
2518 goto fail_vos_VLDBUnlock;
2520 attr.server = ntohl(rx_HostOf(rx_PeerOf(f_server->serv)));
2521 attr.Mask |= VLLIST_SERVER;
2524 if (partition != NULL) {
2525 if (*partition > VOLMAXPARTS) {
2526 tst = ADMVOSPARTITIONTOOLARGE;
2527 goto fail_vos_VLDBUnlock;
2529 attr.partition = *partition;
2530 attr.Mask |= VLLIST_PARTITION;
2532 attr.flag = VLOP_ALLOPERS;
2533 attr.Mask |= VLLIST_FLAG;
2536 if (!VLDB_ListAttributes(c_handle, &attr, &nentries, &entries, &tst)) {
2537 goto fail_vos_VLDBUnlock;
2540 if (nentries <= 0) {
2541 tst = ADMVOSVLDBNOENTRIES;
2542 goto fail_vos_VLDBUnlock;
2545 for(i=0;i<nentries;i++) {
2546 vos_VLDBEntryUnlock(cellHandle, 0,
2547 entries.nbulkentries_val[i].volumeId[RWVOL], &tst);
2551 fail_vos_VLDBUnlock:
2553 if (entries.nbulkentries_val) {
2554 free(entries.nbulkentries_val);
2565 * vos_VLDBEntryLock - lock a vldb entry.
2569 * IN cellHandle - a previously opened cellHandle that corresponds
2570 * to the cell where the vldb entry exists.
2572 * IN callBack - a call back function pointer that may be called to report
2573 * status information. Can be null.
2575 * IN volumeId - the volume id of the vldb entry to be deleted.
2579 * No locks are obtained or released by this function
2583 * Returns != 0 upon successful completion.
2586 int ADMINAPI vos_VLDBEntryLock(
2587 const void *cellHandle,
2588 vos_MessageCallBack_t callBack,
2589 unsigned int volumeId,
2593 afs_status_t tst = 0;
2594 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2597 * Validate arguments
2600 if (!IsValidCellHandle(c_handle, &tst)) {
2601 goto fail_vos_VLDBEntryLock;
2604 tst = ubik_Call(VL_SetLock, c_handle->vos, 0, volumeId, -1, VLOP_DELETE);
2606 goto fail_vos_VLDBEntryLock;
2610 fail_vos_VLDBEntryLock:
2619 * vos_VLDBEntryUnlock - unlock a vldb entry.
2623 * IN cellHandle - a previously opened cellHandle that corresponds
2624 * to the cell where the vldb entry exists.
2626 * IN callBack - a call back function pointer that may be called to report
2627 * status information. Can be null.
2629 * IN volumeId - the volume id of the vldb entry to be unlocked.
2633 * No locks are obtained or released by this function
2637 * Returns != 0 upon successful completion.
2640 int ADMINAPI vos_VLDBEntryUnlock(
2641 const void *cellHandle,
2642 vos_MessageCallBack_t callBack,
2643 unsigned int volumeId,
2647 afs_status_t tst = 0;
2648 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2651 * Validate arguments
2654 if (!IsValidCellHandle(c_handle, &tst)) {
2655 goto fail_vos_VLDBEntryUnlock;
2659 tst = ubik_Call(VL_ReleaseLock, c_handle->vos, 0, volumeId, -1,
2660 LOCKREL_OPCODE | LOCKREL_AFSID | LOCKREL_TIMESTAMP);
2662 goto fail_vos_VLDBEntryUnlock;
2666 fail_vos_VLDBEntryUnlock:
2675 * vos_VLDBReadOnlySiteCreate - create a readonly site for a volume.
2679 * IN cellHandle - a previously opened cellHandle that corresponds
2680 * to the cell where the volume exists.
2682 * IN serverHandle - a previously opened serverHandle that corresponds
2683 * to the server where the new volume should be created.
2685 * IN callBack - a call back function pointer that may be called to report
2686 * status information. Can be null.
2688 * IN partition - the partition where then new volume should be created.
2690 * IN volumeId - the volume id of the volume to be replicated.
2694 * No locks are obtained or released by this function
2698 * Returns != 0 upon successful completion.
2701 int ADMINAPI vos_VLDBReadOnlySiteCreate(
2702 const void *cellHandle,
2703 const void *serverHandle,
2704 vos_MessageCallBack_t callBack,
2705 unsigned int partition,
2706 unsigned int volumeId,
2710 afs_status_t tst = 0;
2711 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2712 file_server_p f_server = (file_server_p) serverHandle;
2715 * Validate arguments
2718 if (!IsValidCellHandle(c_handle, &tst)) {
2719 goto fail_vos_VLDBReadOnlySiteCreate;
2722 if (!IsValidServerHandle(f_server, &tst)) {
2723 goto fail_vos_VLDBReadOnlySiteCreate;
2726 if (partition > VOLMAXPARTS) {
2727 tst = ADMVOSPARTITIONTOOLARGE;
2728 goto fail_vos_VLDBReadOnlySiteCreate;
2731 if (!UV_AddSite(c_handle, ntohl(rx_HostOf(rx_PeerOf(f_server->serv))),
2732 partition, volumeId, &tst)) {
2733 goto fail_vos_VLDBReadOnlySiteCreate;
2737 fail_vos_VLDBReadOnlySiteCreate:
2746 * vos_VLDBReadOnlySiteDelete - delete a replication site for a volume.
2751 * IN cellHandle - a previously opened cellHandle that corresponds
2752 * to the cell where the volume exists.
2754 * IN serverHandle - a previously opened serverHandle that corresponds
2755 * to the server where the volume should be deleted.
2757 * IN callBack - a call back function pointer that may be called to report
2758 * status information. Can be null.
2760 * IN partition - the partition where then volume should be deleted.
2762 * IN volumeId - the volume id of the volume to be deleted.
2766 * No locks are obtained or released by this function
2770 * Returns != 0 upon successful completion.
2773 int ADMINAPI vos_VLDBReadOnlySiteDelete(
2774 const void *cellHandle,
2775 const void *serverHandle,
2776 vos_MessageCallBack_t callBack,
2777 unsigned int partition,
2778 unsigned int volumeId,
2782 afs_status_t tst = 0;
2783 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2784 file_server_p f_server = (file_server_p) serverHandle;
2787 * Validate arguments
2790 if (!IsValidCellHandle(c_handle, &tst)) {
2791 goto fail_vos_VLDBReadOnlySiteDelete;
2794 if (!IsValidServerHandle(f_server, &tst)) {
2795 goto fail_vos_VLDBReadOnlySiteDelete;
2798 if (partition > VOLMAXPARTS) {
2799 tst = ADMVOSPARTITIONTOOLARGE;
2800 goto fail_vos_VLDBReadOnlySiteDelete;
2803 if (!UV_RemoveSite(c_handle, ntohl(rx_HostOf(rx_PeerOf(f_server->serv))),
2804 partition, volumeId, &tst)) {
2805 goto fail_vos_VLDBReadOnlySiteDelete;
2809 fail_vos_VLDBReadOnlySiteDelete:
2818 * vos_VLDBSync - synchronize the vldb with the fileserver.
2822 * IN cellHandle - a previously opened cellHandle that corresponds
2823 * to the cell where the sync should occur.
2825 * IN serverHandle - a previously opened serverHandle that corresponds
2826 * to the server where the sync should occur.
2828 * IN callBack - a call back function pointer that may be called to report
2829 * status information. Can be null.
2831 * IN partition - the partition where the sync should occur. Can be null.
2833 * IN force - force deletion of bad volumes.
2837 * No locks are obtained or released by this function
2841 * Returns != 0 upon successful completion.
2844 int ADMINAPI vos_VLDBSync(
2845 const void *cellHandle,
2846 const void *serverHandle,
2847 vos_MessageCallBack_t callBack,
2848 const unsigned int *partition,
2853 afs_status_t tst = 0;
2854 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2855 file_server_p f_server = (file_server_p) serverHandle;
2861 * Validate arguments
2864 if (!IsValidCellHandle(c_handle, &tst)) {
2865 goto fail_vos_VLDBSync;
2868 if (!IsValidServerHandle(f_server, &tst)) {
2869 goto fail_vos_VLDBSync;
2872 if (partition != NULL) {
2873 if (*partition > VOLMAXPARTS) {
2874 tst = ADMVOSPARTITIONTOOLARGE;
2875 goto fail_vos_VLDBSync;
2877 part = (afs_int32) *partition;
2881 if (force == VOS_FORCE) {
2889 rc = UV_SyncVldb(c_handle, f_server->serv, part, flags, force_flag, &tst);
2900 * vos_VolumeCreate - create a new partition.
2904 * IN cellHandle - a previously opened cellHandle that corresponds
2905 * to the cell where the server lives.
2907 * IN serverHandle - a previously open vos server handle that holds
2908 * the partition where the volume should be create.
2910 * IN callBack - a call back function pointer that may be called to report
2911 * status information. Can be null.
2913 * IN partition - the integer that represents the partition that will
2914 * house the new volume.
2916 * IN volumeName - the name of the new volume.
2918 * IN quota - the quota of the new volume.
2920 * OUT volumeId - the volume id of the newly created volume.
2924 * No locks are obtained or released by this function
2928 * Returns != 0 upon successful completion.
2931 int ADMINAPI vos_VolumeCreate(
2932 const void *cellHandle,
2933 const void *serverHandle,
2934 vos_MessageCallBack_t callBack,
2935 unsigned int partition,
2936 const char *volumeName,
2938 unsigned int *volumeId,
2942 afs_status_t tst = 0;
2943 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
2944 file_server_p f_server = (file_server_p) serverHandle;
2945 vos_partitionEntry_t pinfo;
2946 struct nvldbentry vinfo;
2949 * Validate arguments
2952 if (!IsValidCellHandle(c_handle, &tst)) {
2953 goto fail_vos_VolumeCreate;
2956 if (!IsValidServerHandle(f_server, &tst)) {
2957 goto fail_vos_VolumeCreate;
2960 if (partition > VOLMAXPARTS) {
2961 tst = ADMVOSPARTITIONTOOLARGE;
2962 goto fail_vos_VolumeCreate;
2965 if (!ValidateVolumeName(volumeName, &tst)) {
2966 goto fail_vos_VolumeCreate;
2969 if (volumeId == NULL) {
2970 tst = ADMVOSVOLUMEID;
2971 goto fail_vos_VolumeCreate;
2975 * Check that partition is valid at the server
2978 if (!vos_PartitionGet(cellHandle, serverHandle, 0, partition,
2980 goto fail_vos_VolumeCreate;
2984 * Check that the volume doesn't already exist
2987 if (VLDB_GetEntryByName(c_handle, volumeName, &vinfo, &tst)) {
2988 tst = ADMVOSVOLUMENAMEDUP;
2989 goto fail_vos_VolumeCreate;
2993 * Create the new volume
2996 rc = UV_CreateVolume(c_handle, f_server->serv,
2997 partition, volumeName, quota, volumeId, &tst);
2999 fail_vos_VolumeCreate:
3008 * vos_VolumeDelete - remove a volume.
3012 * IN cellHandle - a previously opened cellHandle that corresponds
3013 * to the cell where the volume exists.
3015 * IN serverHandle - a previously opened serverHandle that corresponds
3016 * to the server where the volume exists.
3018 * IN callBack - a call back function pointer that may be called to report
3019 * status information. Can be null.
3021 * IN partition - the partition where the volume exists.
3023 * IN volumeId - the volume id of the volume to be deleted.
3027 * No locks are obtained or released by this function
3031 * Returns != 0 upon successful completion.
3034 int ADMINAPI vos_VolumeDelete(
3035 const void *cellHandle,
3036 const void *serverHandle,
3037 vos_MessageCallBack_t callBack,
3038 unsigned int partition,
3039 unsigned int volumeId,
3043 afs_status_t tst = 0;
3044 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
3045 file_server_p f_server = (file_server_p) serverHandle;
3046 vos_partitionEntry_t pinfo;
3049 * Validate arguments
3052 if (!IsValidCellHandle(c_handle, &tst)) {
3053 goto fail_vos_VolumeDelete;
3056 if (!IsValidServerHandle(f_server, &tst)) {
3057 goto fail_vos_VolumeDelete;
3060 if (partition > VOLMAXPARTS) {
3061 tst = ADMVOSPARTITIONTOOLARGE;
3062 goto fail_vos_VolumeDelete;
3066 * Check that partition is valid at the server
3069 if (!vos_PartitionGet(cellHandle, serverHandle, 0,
3070 partition, &pinfo, &tst)) {
3071 goto fail_vos_VolumeDelete;
3074 rc = UV_DeleteVolume(c_handle, f_server->serv, partition, volumeId, &tst);
3076 fail_vos_VolumeDelete:
3085 * vos_VolumeRename - rename a volume.
3089 * IN cellHandle - a previously opened cellHandle that corresponds
3090 * to the cell where the volume exists.
3092 * IN serverHandle - a previously opened serverHandle that corresponds
3093 * to the server where the vldb entry exists. Can be null.
3095 * IN callBack - a call back function pointer that may be called to report
3096 * status information. Can be null.
3098 * IN readWriteVolumeId - the volume id of the volume to be renamed.
3100 * IN newVolumeName - the new name.
3104 * No locks are obtained or released by this function
3108 * Returns != 0 upon successful completion.
3111 int ADMINAPI vos_VolumeRename(
3112 const void *cellHandle,
3113 vos_MessageCallBack_t callBack,
3114 unsigned int readWriteVolumeId,
3115 const char *newVolumeName,
3119 afs_status_t tst = 0;
3120 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
3121 struct nvldbentry entry;
3124 * Validate arguments
3127 if (!IsValidCellHandle(c_handle, &tst)) {
3128 goto fail_vos_VolumeRename;
3131 if ((newVolumeName == NULL) || (*newVolumeName == 0)) {
3132 tst = ADMVOSNEWVOLUMENAMENULL;
3133 goto fail_vos_VolumeRename;
3137 * Retrieve the entry
3140 if (!VLDB_GetEntryByID(c_handle, readWriteVolumeId, -1, &entry, &tst)) {
3141 goto fail_vos_VolumeRename;
3144 rc = UV_RenameVolume(c_handle, &entry, newVolumeName, &tst);
3146 fail_vos_VolumeRename:
3155 * vos_VolumeDump - dump a volume
3159 * IN cellHandle - a previously opened cellHandle that corresponds
3160 * to the cell where the volume exists.
3162 * IN serverHandle - a previously opened serverHandle that corresponds
3163 * to the server where the volume exists. Can be null.
3165 * IN callBack - a call back function pointer that may be called to report
3166 * status information. Can be null.
3168 * IN volumeId - the volume id of the volume to be dumped.
3170 * IN startTime - files with modification times >= this time will be dumped.
3172 * IN dumpFile - the file to dump the volume to.
3176 * No locks are obtained or released by this function
3180 * Returns != 0 upon successful completion.
3183 int ADMINAPI vos_VolumeDump(
3184 const void *cellHandle,
3185 const void *serverHandle,
3186 vos_MessageCallBack_t callBack,
3187 unsigned int *partition,
3188 unsigned int volumeId,
3189 unsigned int startTime,
3190 const char *dumpFile,
3194 afs_status_t tst = 0;
3195 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
3196 file_server_p f_server = (file_server_p) serverHandle;
3197 afs_int32 server, part, voltype;
3198 struct nvldbentry entry;
3201 * Validate arguments
3204 if (!IsValidCellHandle(c_handle, &tst)) {
3205 goto fail_vos_VolumeDump;
3208 if (serverHandle != NULL) {
3209 if (!IsValidServerHandle(f_server, &tst)) {
3210 goto fail_vos_VolumeDump;
3215 * You must specify both the serverHandle and the partition
3218 if (serverHandle || partition) {
3219 if (!serverHandle || !partition) {
3220 tst = ADMVOSSERVERANDPARTITION;
3221 goto fail_vos_VolumeDump;
3223 if (*partition > VOLMAXPARTS) {
3224 tst = ADMVOSPARTITIONTOOLARGE;
3225 goto fail_vos_VolumeDump;
3227 server = ntohl(rx_HostOf(rx_PeerOf(f_server->serv)));
3231 if (!GetVolumeInfo(c_handle, volumeId, &entry, &server,
3232 &part, &voltype, &tst)) {
3233 goto fail_vos_VolumeDump;
3237 if ((dumpFile == NULL) || (*dumpFile == 0)) {
3238 tst = ADMVOSDUMPFILENULL;
3239 goto fail_vos_VolumeDump;
3242 rc = UV_DumpVolume(c_handle, volumeId, server, part, startTime,
3245 fail_vos_VolumeDump:
3254 * vos_VolumeRestore - restore a volume from a dump
3258 * IN cellHandle - a previously opened cellHandle that corresponds
3259 * to the cell where the volume exists.
3261 * IN serverHandle - a previously opened serverHandle that corresponds
3262 * to the server where the volume exists.
3264 * IN callBack - a call back function pointer that may be called to report
3265 * status information. Can be null.
3267 * IN partition - the partition where the volume exists.
3269 * IN volumeId - the volume id of the volume to be restored.
3271 * IN volumeName - the volume name of the volume to be restored.
3273 * IN dumpFile - the file from which to restore the volume.
3275 * IN dumpType - the type of dump to perform.
3279 * No locks are obtained or released by this function
3283 * Returns != 0 upon successful completion.
3286 int ADMINAPI vos_VolumeRestore(
3287 const void *cellHandle,
3288 const void *serverHandle,
3289 vos_MessageCallBack_t callBack,
3290 unsigned int partition,
3291 unsigned int *volumeId,
3292 const char *volumeName,
3293 const char *dumpFile,
3294 vos_volumeRestoreType_t dumpType,
3298 afs_status_t tst = 0;
3299 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
3300 file_server_p f_server = (file_server_p) serverHandle;
3301 struct nvldbentry entry;
3302 afs_int32 volid, server;
3305 int restoreflags = 0;
3306 afs_int32 Oserver, Opart, Otype;
3307 struct nvldbentry Oentry;
3311 * Validate arguments
3314 if (!IsValidCellHandle(c_handle, &tst)) {
3315 goto fail_vos_VolumeRestore;
3318 if (serverHandle != NULL) {
3319 if (!IsValidServerHandle(f_server, &tst)) {
3320 goto fail_vos_VolumeRestore;
3325 * Must pass volumeName
3328 if ((volumeName == NULL) || (*volumeName == 0)) {
3329 tst = ADMVOSVOLUMENAMENULL;
3330 goto fail_vos_VolumeRestore;
3333 if (!ValidateVolumeName(volumeName, &tst)) {
3334 goto fail_vos_VolumeRestore;
3338 * If volumeId is passed, it must be a valid volume id
3341 if (volumeId != NULL) {
3342 if (!VLDB_GetEntryByID(c_handle, *volumeId, -1, &entry, &tst)) {
3343 goto fail_vos_VolumeRestore;
3350 server = ntohl(rx_HostOf(rx_PeerOf(f_server->serv)));
3352 if (partition > VOLMAXPARTS) {
3353 tst = ADMVOSPARTITIONTOOLARGE;
3354 goto fail_vos_VolumeRestore;
3358 * Check that dumpFile exists and can be accessed
3361 fd = open(dumpFile, 0);
3362 if ((fd < 0) || (fstat(fd, &status) < 0)) {
3364 tst = ADMVOSDUMPFILEOPENFAIL;
3365 goto fail_vos_VolumeRestore;
3370 if (!VLDB_GetEntryByName(c_handle, volumeName, &entry, &tst)) {
3371 restoreflags = RV_FULLRST;
3372 } else if (Lp_GetRwIndex(c_handle, &entry, 0) == -1) {
3373 restoreflags = RV_FULLRST;
3375 volid = entry.volumeId[RWVOL];
3376 } else if ((entry.volumeId[RWVOL] != 0) &&
3377 (entry.volumeId[RWVOL] != volid)) {
3378 volid = entry.volumeId[RWVOL];
3383 volid = entry.volumeId[RWVOL];
3384 } else if ((entry.volumeId[RWVOL] != 0) &&
3385 (entry.volumeId[RWVOL] != volid)) {
3386 volid = entry.volumeId[RWVOL];
3390 * If the vldb says the same volume exists somewhere else
3391 * the caller must specify a full restore, not an incremental
3394 if (dumpType == VOS_RESTORE_FULL) {
3395 restoreflags = RV_FULLRST;
3399 * Check to see if the volume exists where the caller said
3401 if (!GetVolumeInfo(c_handle, volid, &Oentry, &Oserver, &Opart,
3403 goto fail_vos_VolumeRestore;
3405 if (!VLDB_IsSameAddrs(c_handle, Oserver, server, &equal, &tst)) {
3406 goto fail_vos_VolumeRestore;
3410 tst = ADMVOSRESTOREVOLEXIST;
3411 goto fail_vos_VolumeRestore;
3416 rc = UV_RestoreVolume(c_handle, server, partition, volid, volumeName,
3417 restoreflags, dumpFile, &tst);
3419 fail_vos_VolumeRestore:
3428 * vos_VolumeOnline - bring a volume online.
3432 * IN serverHandle - a previously opened serverHandle that corresponds
3433 * to the server where the volume exists.
3435 * IN callBack - a call back function pointer that may be called to report
3436 * status information. Can be null.
3438 * IN partition - the partition where the volume exists.
3440 * IN volumeId - the volume id of the volume to be brought online.
3444 * No locks are obtained or released by this function
3448 * Returns != 0 upon successful completion.
3451 int ADMINAPI vos_VolumeOnline(
3452 const void *serverHandle,
3453 vos_MessageCallBack_t callBack,
3454 unsigned int partition,
3455 unsigned int volumeId,
3456 unsigned int sleepTime,
3457 vos_volumeOnlineType_t volumeStatus,
3461 afs_status_t tst = 0;
3462 file_server_p f_server = (file_server_p) serverHandle;
3466 * Validate arguments
3469 if (!IsValidServerHandle(f_server, &tst)) {
3470 goto fail_vos_VolumeOnline;
3473 if (partition > VOLMAXPARTS) {
3474 tst = ADMVOSPARTITIONIDTOOLARGE;
3475 goto fail_vos_VolumeOnline;
3478 if (volumeStatus == VOS_ONLINE_BUSY) {
3482 rc = UV_SetVolume(f_server->serv, partition, volumeId, up, 0,
3485 fail_vos_VolumeOnline:
3494 * vos_VolumeOffline - take a volume offline.
3498 * IN serverHandle - a previously opened serverHandle that corresponds
3499 * to the server where the volume exists.
3501 * IN callBack - a call back function pointer that may be called to report
3502 * status information. Can be null.
3504 * IN partition - the partition where the volume exists.
3506 * IN volumeId - the volume id of the volume to be taken offline.
3510 * No locks are obtained or released by this function
3514 * Returns != 0 upon successful completion.
3517 int ADMINAPI vos_VolumeOffline(
3518 const void *serverHandle,
3519 vos_MessageCallBack_t callBack,
3520 unsigned int partition,
3521 unsigned int volumeId,
3525 afs_status_t tst = 0;
3526 file_server_p f_server = (file_server_p) serverHandle;
3529 * Validate arguments
3532 if (!IsValidServerHandle(f_server, &tst)) {
3533 goto fail_vos_VolumeOffline;
3536 if (partition > VOLMAXPARTS) {
3537 tst = ADMVOSPARTITIONIDTOOLARGE;
3538 goto fail_vos_VolumeOffline;
3541 rc = UV_SetVolume(f_server->serv, partition, volumeId, ITOffline,
3542 VTOutOfService, 0, &tst);
3544 fail_vos_VolumeOffline:
3553 * copyvolintXInfo - copy a struct volintXInfo to a vos_volumeEntry_p.
3557 * IN source - the volintXInfo structure to copy.
3559 * OUT dest - the vos_volumeEntry_t to fill
3563 * No locks are obtained or released by this function
3567 * Returns != 0 upon successful completion.
3570 static int copyvolintXInfo(
3571 struct volintXInfo *source,
3572 vos_volumeEntry_p dest,
3576 afs_status_t tst = 0;
3580 * If the volume is not marked OK, all the other fields are invalid
3581 * We take the extra step of blanking out dest here to prevent the
3582 * user from seeing stale data from a previous call
3585 memset(dest, 0, sizeof(dest));
3587 switch(source->status){
3589 dest->status = VOS_OK;
3592 dest->status = VOS_SALVAGE;
3595 dest->status = VOS_NO_VNODE;
3598 dest->status = VOS_NO_VOL;
3601 dest->status = VOS_VOL_EXISTS;
3604 dest->status = VOS_NO_SERVICE;
3607 dest->status = VOS_OFFLINE;
3610 dest->status = VOS_ONLINE;
3613 dest->status = VOS_DISK_FULL;
3616 dest->status = VOS_OVER_QUOTA;
3619 dest->status = VOS_BUSY;
3622 dest->status = VOS_MOVED;
3627 * Check to see if the entry is marked ok before copying all the
3631 if (dest->status == VOS_OK) {
3632 strcpy(dest->name, source->name);
3633 dest->id = source->volid;
3634 if (source->type == 0) {
3635 dest->type = VOS_READ_WRITE_VOLUME;
3636 } else if (source->type == 1) {
3637 dest->type = VOS_READ_ONLY_VOLUME;
3638 } else if (source->type == 2) {
3639 dest->type = VOS_BACKUP_VOLUME;
3641 dest->backupId = source->backupID;
3642 dest->readWriteId = source->parentID;
3643 dest->readOnlyId = source->cloneID;
3644 dest->copyCreationDate = source->copyDate;
3645 dest->creationDate = source->creationDate;
3646 dest->lastAccessDate = source->accessDate;
3647 dest->lastUpdateDate = source->updateDate;
3648 dest->lastBackupDate = source->backupDate;
3649 dest->accessesSinceMidnight = source->dayUse;
3650 dest->fileCount = source->filecount;
3651 dest->maxQuota = source->maxquota;
3652 dest->currentSize = source->size;
3653 if (source->inUse == 1) {
3654 dest->volumeDisposition = VOS_ONLINE;
3656 dest->volumeDisposition = VOS_OFFLINE;
3659 for(i=0;i<VOS_VOLUME_READ_WRITE_STATS_NUMBER;i++) {
3660 dest->readStats[i] = source->stat_reads[i];
3661 dest->writeStats[i] = source->stat_writes[i];
3664 for(i=0;i<VOS_VOLUME_TIME_STATS_NUMBER;i++) {
3665 dest->fileAuthorWriteSameNetwork[i] = source->stat_fileSameAuthor[i];
3666 dest->fileAuthorWriteDifferentNetwork[i] =
3667 source->stat_fileDiffAuthor[i];
3668 dest->dirAuthorWriteSameNetwork[i] = source->stat_dirSameAuthor[i];
3669 dest->dirAuthorWriteDifferentNetwork[i] = source->stat_dirDiffAuthor[i];
3682 * vos_VolumeGet - get information about a particular volume.
3686 * IN cellHandle - a previously opened cellHandle that corresponds
3687 * to the cell where the volume exists.
3689 * IN serverHandle - a previously opened serverHandle that corresponds
3690 * to the server where the volume exists.
3692 * IN callBack - a call back function pointer that may be called to report
3693 * status information. Can be null.
3695 * IN partition - the partition where the volume exists.
3697 * IN volumeId - the volume id of the volume to be retrieved.
3699 * OUT volumeP - upon successful completion, contains the information about the
3704 * No locks are obtained or released by this function
3708 * Returns != 0 upon successful completion.
3711 int ADMINAPI vos_VolumeGet(
3712 const void *cellHandle,
3713 const void *serverHandle,
3714 vos_MessageCallBack_t callBack,
3715 unsigned int partition,
3716 unsigned int volumeId,
3717 vos_volumeEntry_p volumeP,
3721 afs_status_t tst = 0;
3722 file_server_p f_server = (file_server_p) serverHandle;
3723 struct volintXInfo *info = NULL;
3726 * Validate arguments
3729 if (!IsValidServerHandle(f_server, &tst)) {
3730 goto fail_vos_VolumeGet;
3733 if (partition > VOLMAXPARTS) {
3734 tst = ADMVOSPARTITIONIDTOOLARGE;
3735 goto fail_vos_VolumeGet;
3738 if (volumeP == NULL) {
3739 tst = ADMVOSVOLUMEPNULL;
3740 goto fail_vos_VolumeGet;
3744 * Retrieve the information for the volume
3747 if (!UV_XListOneVolume(f_server->serv, partition, volumeId, &info, &tst)) {
3748 goto fail_vos_VolumeGet;
3752 * Copy the volume info to our structure
3755 if (!copyvolintXInfo(info, volumeP, &tst)) {
3756 goto fail_vos_VolumeGet;
3773 * The iterator functions and data for the volume retrieval functions.
3776 typedef struct volume_get {
3777 struct volintXInfo *vollist;
3778 afs_int32 total; /* total number of volumes at this partition */
3779 afs_int32 index; /* index to the current volume */
3780 vos_volumeEntry_t entry[CACHED_ITEMS]; /* the cache of entries */
3781 } volume_get_t, *volume_get_p;
3783 static int GetVolumeRPC(
3787 int *last_item_contains_data,
3791 afs_status_t tst = 0;
3792 volume_get_p entry = (volume_get_p) rpc_specific;
3795 * Copy the next entry into the cache
3798 if (!copyvolintXInfo(&entry->vollist[entry->index],
3799 &entry->entry[slot],
3801 goto fail_GetVolumeRPC;
3806 * See if we've processed all the entries
3810 if (entry->index == entry->total) {
3812 *last_item_contains_data = 1;
3824 static int GetVolumeFromCache(
3831 afs_status_t tst = 0;
3832 volume_get_p entry = (volume_get_p) rpc_specific;
3834 memcpy(dest, (const void *) &entry->entry[slot],
3835 sizeof(vos_volumeEntry_t));
3845 static int DestroyVolume(
3850 afs_status_t tst = 0;
3851 volume_get_p entry = (volume_get_p) rpc_specific;
3853 if (entry->vollist != NULL) {
3854 free(entry->vollist);
3866 * vos_VolumeGetBegin - begin to iterator over the list of volumes at a server.
3870 * IN cellHandle - a previously opened cellHandle that corresponds
3871 * to the cell where the volumes exist.
3873 * IN serverHandle - a handle to the server where the volumes exist.
3875 * IN callBack - a call back function pointer that may be called to report
3876 * status information. Can be null.
3878 * IN partition - the partition whose volumes should be listed. Can be null.
3880 * OUT iterationIdP - upon successful completion, contains an iterator that
3881 * can be passed to vos_VolumeGetBegin.
3885 * No locks are obtained or released by this function
3889 * Returns != 0 upon successful completion.
3892 int ADMINAPI vos_VolumeGetBegin(
3893 const void *cellHandle,
3894 const void *serverHandle,
3895 vos_MessageCallBack_t callBack,
3896 unsigned int partition,
3897 void **iterationIdP,
3901 afs_status_t tst = 0;
3902 file_server_p f_server = (file_server_p) serverHandle;
3903 afs_admin_iterator_p iter = (afs_admin_iterator_p) malloc(sizeof(afs_admin_iterator_t));
3904 volume_get_p entry = (volume_get_p) calloc(1, sizeof(volume_get_t));
3907 * Validate arguments
3910 if (!IsValidServerHandle(f_server, &tst)) {
3911 goto fail_vos_VolumeGetBegin;
3914 if (partition > VOLMAXPARTS) {
3915 tst = ADMVOSPARTITIONIDTOOLARGE;
3916 goto fail_vos_VolumeGetBegin;
3919 if ((iter == NULL) || (entry == NULL)) {
3921 goto fail_vos_VolumeGetBegin;
3925 * Get a list of all the volumes contained in the partition at the
3929 if (!UV_XListVolumes(f_server->serv, partition, 1, &entry->vollist,
3930 &entry->total, &tst)) {
3931 goto fail_vos_VolumeGetBegin;
3934 if (entry->total == 0) {
3935 if (!IteratorInit(iter, (void *) entry, NULL, NULL, NULL, NULL, &tst)) {
3936 goto fail_vos_VolumeGetBegin;
3938 iter->done_iterating = 1;
3939 iter->st = ADMITERATORDONE;
3941 if (!IteratorInit(iter, (void *) entry, GetVolumeRPC,
3942 GetVolumeFromCache, NULL, DestroyVolume, &tst)) {
3943 goto fail_vos_VolumeGetBegin;
3946 *iterationIdP = (void *) iter;
3949 fail_vos_VolumeGetBegin:
3955 if (entry != NULL) {
3967 * vos_VolumeGetNext - get information about the next volume.
3971 * IN iterationId - an iterator previously returned by
3972 * vos_VolumeGetBegin
3974 * OUT volumeP - a pointer to a vos_volumeEntry_t
3975 * that upon successful completion contains information about the
3980 * The iterator is locked while the next item is retrieved.
3984 * Returns != 0 upon successful completion.
3987 int ADMINAPI vos_VolumeGetNext(
3988 const void *iterationId,
3989 vos_volumeEntry_p volumeP,
3993 afs_status_t tst = 0;
3994 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
3997 tst = ADMITERATORNULL;
3998 goto fail_vos_VolumeGetNext;
4001 if (volumeP == NULL) {
4002 tst = ADMVOSVOLUMEPNULL;
4003 goto fail_vos_VolumeGetNext;
4006 rc = IteratorNext(iter, (void *) volumeP, &tst);
4008 fail_vos_VolumeGetNext:
4017 * vos_VolumeGetDone - finish using a volume iterator.
4021 * IN iterationId - an iterator previously returned by vos_VolumeGetBegin
4025 * The iterator is locked and then destroyed.
4029 * Returns != 0 upon successful completion.
4032 int ADMINAPI vos_VolumeGetDone(
4033 const void *iterationId,
4037 afs_status_t tst = 0;
4038 afs_admin_iterator_p iter = (afs_admin_iterator_p) iterationId;
4041 * Validate arguments
4045 tst = ADMITERATORNULL;
4046 goto fail_vos_VolumeGetDone;
4049 rc = IteratorDone(iter, &tst);
4051 fail_vos_VolumeGetDone:
4060 * vos_VolumeMove - move a volume from one server to another.
4064 * IN cellHandle - a previously opened cellHandle that corresponds
4065 * to the cell where the volume exists.
4067 * IN callBack - a call back function pointer that may be called to report
4068 * status information. Can be null.
4070 * IN volumeId - the volume id of the volume to be moved.
4072 * IN fromServer - a previously opened serverHandle that corresponds
4073 * to the server where the volume currently resides.
4075 * IN fromPartition - the partition where the volume currently resides.
4077 * IN toServer - a previously opened serverHandle that corresponds
4078 * to the server where the volume will be moved.
4080 * IN toPartition - the partition where the volume will be moved.
4084 * No locks are obtained or released by this function
4088 * Returns != 0 upon successful completion.
4091 int ADMINAPI vos_VolumeMove(
4092 const void *cellHandle,
4093 vos_MessageCallBack_t callBack,
4094 unsigned int volumeId,
4095 const void *fromServer,
4096 unsigned int fromPartition,
4097 const void *toServer,
4098 unsigned int toPartition,
4102 afs_status_t tst = 0;
4103 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
4104 file_server_p from_server = (file_server_p) fromServer;
4105 file_server_p to_server = (file_server_p) toServer;
4106 afs_int32 from_server_addr = ntohl(rx_HostOf(rx_PeerOf(from_server->serv)));
4107 afs_int32 to_server_addr = ntohl(rx_HostOf(rx_PeerOf(to_server->serv)));
4108 afs_int32 from_partition = fromPartition;
4109 afs_int32 to_partition = toPartition;
4112 * Validate arguments
4115 if (!IsValidCellHandle(c_handle, &tst)) {
4116 goto fail_vos_VolumeMove;
4119 if (!IsValidServerHandle(from_server, &tst)) {
4120 goto fail_vos_VolumeMove;
4123 if (!IsValidServerHandle(to_server, &tst)) {
4124 goto fail_vos_VolumeMove;
4127 if (fromPartition > VOLMAXPARTS) {
4128 tst = ADMVOSPARTITIONIDTOOLARGE;
4129 goto fail_vos_VolumeMove;
4132 if (toPartition > VOLMAXPARTS) {
4133 tst = ADMVOSPARTITIONIDTOOLARGE;
4134 goto fail_vos_VolumeMove;
4141 rc = UV_MoveVolume(c_handle, volumeId, from_server_addr, from_partition,
4142 to_server_addr, to_partition, &tst);
4144 fail_vos_VolumeMove:
4153 * vos_VolumeRelease - release a volume.
4157 * IN cellHandle - a previously opened cellHandle that corresponds
4158 * to the cell where the volume exists.
4160 * IN callBack - a call back function pointer that may be called to report
4161 * status information. Can be null.
4163 * IN volumeId - the volume to be released.
4165 * IN force - force a complete release.
4169 * No locks are obtained or released by this function
4173 * Returns != 0 upon successful completion.
4176 int ADMINAPI vos_VolumeRelease(
4177 const void *cellHandle,
4178 vos_MessageCallBack_t callBack,
4179 unsigned int volumeId,
4184 afs_status_t tst = 0;
4185 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
4186 afs_int32 server, part, forc = 0, voltype, volume;
4187 struct nvldbentry entry;
4190 * Validate arguments
4193 if (!IsValidCellHandle(c_handle, &tst)) {
4194 goto fail_vos_VolumeRelease;
4197 if (!GetVolumeInfo(c_handle, volumeId, &entry, &server,
4198 &part, &voltype, &tst)) {
4199 goto fail_vos_VolumeRelease;
4202 if (force == VOS_FORCE) {
4207 rc = UV_ReleaseVolume(c_handle, volume, server, part, forc, &tst);
4209 fail_vos_VolumeRelease:
4218 * vos_VolumeZap - forcibly delete a volume.
4222 * IN cellHandle - a previously opened cellHandle that corresponds
4223 * to the cell where the volume exists.
4225 * IN serverHandle - a previously opened serverHandle that corresponds
4226 * to the server where the volume exists.
4228 * IN callBack - a call back function pointer that may be called to report
4229 * status information. Can be null.
4231 * IN partition - the partition where the volume exists.
4233 * IN volumeId - the volume id of the vldb entry to be deleted.
4235 * IN force - force the deletion of bad volumes.
4239 * No locks are obtained or released by this function
4243 * Returns != 0 upon successful completion.
4246 int ADMINAPI vos_VolumeZap(
4247 const void *cellHandle,
4248 const void *serverHandle,
4249 vos_MessageCallBack_t callBack,
4250 unsigned int partition,
4251 unsigned int volumeId,
4256 afs_status_t tst = 0;
4257 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
4258 file_server_p f_server = (file_server_p) serverHandle;
4261 * Verify that the cellHandle is capable of making vos rpc's
4264 if (!IsValidCellHandle(c_handle, &tst)) {
4265 goto fail_vos_VolumeZap;
4268 if (!IsValidServerHandle(f_server, &tst)) {
4269 goto fail_vos_VolumeZap;
4272 if (force == VOS_FORCE) {
4273 rc = UV_NukeVolume(c_handle, f_server->serv, partition, volumeId, &tst);
4275 rc = UV_VolumeZap(c_handle, f_server->serv, partition, volumeId, &tst);
4287 * vos_PartitionNameToId - translate a string representing a partition
4292 * IN partitionName - a string representing a partition. Must be of
4295 * OUT partitionId - a number containing the partition id upon successful
4300 * No locks are obtained or released by this function
4304 * Returns != 0 upon successful completion.
4307 int ADMINAPI vos_PartitionNameToId(
4308 const char *partitionName,
4309 unsigned int *partitionId,
4313 afs_status_t tst = 0;
4314 size_t partition_name_len;
4318 * Validate arguments
4321 if (partitionName == NULL) {
4322 tst = ADMVOSPARTITIONNAMENULL;
4323 goto fail_vos_PartitionNameToId;
4326 if (partitionId == NULL) {
4327 tst = ADMVOSPARTITIONIDNULL;
4328 goto fail_vos_PartitionNameToId;
4332 * Check that string begins with /vicep
4335 if (strncmp(partitionName, VICE_PARTITION_PREFIX, VICE_PREFIX_SIZE)) {
4336 tst = ADMVOSPARTITIONNAMEINVALID;
4337 goto fail_vos_PartitionNameToId;
4341 * Check that the string is either one or two characters
4342 * longer than VICE_PREFIX_SIZE
4345 partition_name_len = strlen(partitionName);
4347 if (partition_name_len == VICE_PREFIX_SIZE) {
4348 tst = ADMVOSPARTITIONNAMETOOSHORT;
4349 goto fail_vos_PartitionNameToId;
4352 if (partition_name_len > (VICE_PREFIX_SIZE + 2)) {
4353 tst = ADMVOSPARTITIONNAMETOOLONG;
4354 goto fail_vos_PartitionNameToId;
4358 * Check that all characters past the prefix are lower case
4361 for(i=VICE_PREFIX_SIZE;i<partition_name_len;i++) {
4362 if (!islower(partitionName[i])) {
4363 tst = ADMVOSPARTITIONNAMENOTLOWER;
4364 goto fail_vos_PartitionNameToId;
4369 * Convert the name to a number
4372 if (partitionName[VICE_PREFIX_SIZE + 1] == 0) {
4373 *partitionId = partitionName[VICE_PREFIX_SIZE] - 'a';
4375 *partitionId = (partitionName[VICE_PREFIX_SIZE] - 'a') * 26 +
4376 (partitionName[VICE_PREFIX_SIZE + 1] - 'a') + 26;
4379 if (*partitionId > VOLMAXPARTS) {
4380 tst = ADMVOSPARTITIONIDTOOLARGE;
4381 goto fail_vos_PartitionNameToId;
4385 fail_vos_PartitionNameToId:
4394 * vos_PartitionIdToName - translate a number representing a partition
4395 * to a character string.
4399 * IN partitionId - an integer representing the partition.
4401 * OUT partitionName - a string containing the converted partition ID
4402 * upon successful completion.
4406 * No locks are obtained or released by this function
4410 * Returns != 0 upon successful completion.
4413 int ADMINAPI vos_PartitionIdToName(
4414 unsigned int partitionId,
4415 char *partitionName,
4419 afs_status_t tst = 0;
4421 if (partitionId > VOLMAXPARTS) {
4422 tst = ADMVOSPARTITIONIDTOOLARGE;
4423 goto fail_vos_PartitionIdToName;
4426 if (partitionName == NULL) {
4427 tst = ADMVOSPARTITIONNAMENULL;
4428 goto fail_vos_PartitionIdToName;
4431 if(partitionId < 26) {
4432 strcpy(partitionName, VICE_PARTITION_PREFIX);
4433 partitionName[6] = partitionId + 'a';
4434 partitionName[7] = '\0';
4436 strcpy(partitionName, VICE_PARTITION_PREFIX);
4438 partitionName[6] = 'a' + (partitionId/26);
4439 partitionName[7] = 'a' + (partitionId%26);
4440 partitionName[8] = '\0';
4444 fail_vos_PartitionIdToName:
4453 * vos_VolumeQuotaChange - change the quota of a volume.
4457 * IN cellHandle - a previously opened cellHandle that corresponds
4458 * to the cell where the volume exists.
4460 * IN serverHandle - a previously opened serverHandle that corresponds
4461 * to the server where the volume exists.
4463 * IN callBack - a call back function pointer that may be called to report
4464 * status information. Can be null.
4466 * IN partition - the partition where the volume exists.
4468 * IN volumeId - the volume id of the volume to be modified.
4470 * IN volumeQuota - the new volume quota.
4474 * No locks are obtained or released by this function
4478 * Returns != 0 upon successful completion.
4481 int ADMINAPI vos_VolumeQuotaChange(
4482 const void *cellHandle,
4483 const void *serverHandle,
4484 vos_MessageCallBack_t callBack,
4485 unsigned int partition,
4486 unsigned int volumeId,
4487 unsigned int volumeQuota,
4491 afs_status_t tst = 0;
4492 afs_cell_handle_p c_handle = (afs_cell_handle_p) cellHandle;
4493 file_server_p f_server = (file_server_p) serverHandle;
4496 struct volintInfo tstatus;
4497 int active_trans = 0;
4500 * Verify that the cellHandle is capable of making vos rpc's
4503 if (!IsValidCellHandle(c_handle, &tst)) {
4504 goto fail_vos_VolumeQuotaChange;
4507 if (!IsValidServerHandle(f_server, &tst)) {
4508 goto fail_vos_VolumeQuotaChange;
4511 memset((void *) &tstatus, 0, sizeof(tstatus));
4512 tstatus.dayUse = -1;
4513 tstatus.maxquota = volumeQuota;
4515 tst = AFSVolTransCreate(f_server->serv, volumeId, partition, ITBusy, &ttid);
4517 goto fail_vos_VolumeQuotaChange;
4521 tst = AFSVolSetInfo(f_server->serv, ttid, &tstatus);
4523 goto fail_vos_VolumeQuotaChange;
4527 fail_vos_VolumeQuotaChange:
4530 afs_status_t tst2 = 0;
4531 tst2 = AFSVolEndTrans(f_server->serv, ttid, &rcode);