AFS
view release on metacpan or search on metacpan
#endif
#include <ubik.h>
#include <rx/rxkad.h>
#include <afs/vldbint.h>
#include <afs/volser.h>
#ifndef RV_RDONLY
#define RV_FULLRST 0x000001
#define RV_OFFLINE 0x000002
#define RV_CRDUMP 0x000010
#define RV_CRKEEP 0x000020
#define RV_CRNEW 0x000040
#define RV_LUDUMP 0x000100
#define RV_LUKEEP 0x000200
#define RV_LUNEW 0x000400
#define RV_RDONLY 0x010000
#define RV_CPINCR 0x020000
#define RV_NOVLDB 0x040000
#define RV_NOCLONE 0x080000
#define RV_NODEL 0x100000
#endif
#include <afs/vlserver.h>
#include <afs/volint.h>
#include <afs/cmd.h>
#include <afs/usd.h>
#include <afs/ptclient.h>
#include <afs/pterror.h>
#include <afs/print.h>
#include <afs/kauth.h>
#include <afs/kautils.h>
#include <afs/bosint.h>
#include <afs/bnode.h>
#include <afs/ktime.h>
#if defined(AFS_OLD_COM_ERR)
#include <com_err.h>
#else
#include <afs/com_err.h>
#endif
#include <des.h>
#if defined(AFS_3_4) || defined(AFS_3_5)
#else
#define int32 afs_int32
#define uint32 afs_uint32
#endif
const char *const xs_version = "AFS.xs (Version 2.6.4)";
/* here because it seemed too painful to #define KERNEL before #inc afs.h */
struct VenusFid {
int32 Cell;
struct AFSFid Fid;
};
/* tpf nog 03/29/99 */
/* the following was added by leg@andrew, 10/9/96 */
/*#ifdef __hpux*//* only on hp700_ux90 systems */
#if defined(__hpux) || defined(_AIX) || defined(sun) || defined(__sun__) || defined(__sgi) || defined(__linux)
static int32 name_is_numeric(char *);
#endif
typedef SV *AFS__ACL;
typedef struct ktc_principal *AFS__KTC_PRINCIPAL;
typedef struct ktc_token *AFS__KTC_TOKEN;
typedef struct ktc_encryptionKey *AFS__KTC_EKEY;
typedef struct ubik_client *AFS__KAS;
typedef struct ubik_client *AFS__PTS;
typedef struct ubik_client *AFS__VLDB;
typedef struct ubik_client *AFS__VOS;
typedef struct rx_connection *AFS__BOS;
extern struct ubik_client *cstruct;
#include "afs_prototypes.h"
extern int afs_setpag();
static rxkad_level vsu_rxkad_level = rxkad_clear;
static struct ktc_token the_null_token;
static int32 convert_numeric_names = 1;
static int32 rx_initialized = 0;
#define MAXSIZE 2048
#define MAXINSIZE 1300
#ifndef MAXPATHLEN
#define MAXPATHLEN 1024
#endif
#define AFS_ASK 0
#define AFS_ABORT 1
#define AFS_FULL 2
#define AFS_INC 3
#ifdef AFS_PTHREAD_ENV
#undef clock_haveCurrentTime
#undef clock_UpdateTime
struct clock clock_now;
#endif /* AFS_PTHREAD_ENV*/
/* error handling macros */
#define ERROR_EXIT(code) {error=(code); goto error_exit;}
#define SETCODE(code) set_code(code)
#define BSETCODE(code, msg) bv_set_code(code, msg)
#define VSETCODE(code, msg) bv_set_code(code, msg)
#define KSETCODE(code, msg) k_set_code(code, msg)
#define PSETCODE(msg) p_set_code(msg)
static int32 raise_exception = 0;
void safe_hv_store (HV* ahv,char * key ,int i ,SV * asv,int j) {
if (! hv_store(ahv, key, i, asv, j)) {
fprintf(stderr,"Panic ... internal error. hv_store failed.\n");
exit(1);
}
return;
}
static void bv_set_code(code, msg)
int32 code;
const char *msg;
{
SV *sv = get_sv("AFS::CODE", TRUE);
sv_setiv(sv, (IV) code);
/* printf("BV_SET_CODE %s (%d)\n", msg, code); */
if (code == 0) {
sv_setpv(sv, "");
}
else {
if (raise_exception) {
char buffer[1024];
sprintf(buffer, "AFS exception: %s (%d)", msg, code);
croak(buffer);
sprintf(buffer, "Volume needs to be salvaged\n");
break;
case VNOVNODE:
sprintf(buffer, "Bad vnode number quoted\n");
break;
case VNOVOL:
sprintf(buffer, "Volume not attached, does not exist, or not on line\n");
break;
case VVOLEXISTS:
sprintf(buffer, "Volume already exists\n");
break;
case VNOSERVICE:
sprintf(buffer, "Volume is not in service\n");
break;
case VOFFLINE:
sprintf(buffer, "Volume is off line\n");
break;
case VONLINE:
sprintf(buffer, "Volume is already on line\n");
break;
case VDISKFULL:
sprintf(buffer, "Partition is full\n");
break;
case VOVERQUOTA:
sprintf(buffer, "Volume max quota exceeded\n");
break;
case VBUSY:
sprintf(buffer, "Volume temporarily unavailable\n");
break;
case VMOVED:
sprintf(buffer, "Volume has moved to another server\n");
break;
case VL_IDEXIST:
sprintf(buffer, "VLDB: volume Id exists in the vldb\n");
break;
case VL_IO:
sprintf(buffer, "VLDB: a read terminated too early\n");
break;
case VL_NAMEEXIST:
sprintf(buffer, "VLDB: volume entry exists in the vldb\n");
break;
case VL_CREATEFAIL:
sprintf(buffer, "VLDB: internal creation failure\n");
break;
case VL_NOENT:
sprintf(buffer, "VLDB: no such entry\n");
break;
case VL_EMPTY:
sprintf(buffer, "VLDB: vldb database is empty\n");
break;
case VL_ENTDELETED:
sprintf(buffer, "VLDB: entry is deleted (soft delete)\n");
break;
case VL_BADNAME:
sprintf(buffer, "VLDB: volume name is illegal\n");
break;
case VL_BADINDEX:
sprintf(buffer, "VLDB: index was out of range\n");
break;
case VL_BADVOLTYPE:
sprintf(buffer, "VLDB: bad volume type\n");
break;
case VL_BADSERVER:
sprintf(buffer, "VLDB: illegal server number (not within limits)\n");
break;
case VL_BADPARTITION:
sprintf(buffer, "VLDB: bad partition number\n");
break;
case VL_REPSFULL:
sprintf(buffer, "VLDB: run out of space for replication sites\n");
break;
case VL_NOREPSERVER:
sprintf(buffer, "VLDB: no such repsite server exists\n");
break;
case VL_DUPREPSERVER:
sprintf(buffer, "VLDB: replication site server already exists\n");
break;
case VL_RWNOTFOUND:
sprintf(buffer, "VLDB: parent r/w entry not found\n");
break;
case VL_BADREFCOUNT:
sprintf(buffer, "VLDB: illegal reference count number\n");
break;
case VL_SIZEEXCEEDED:
sprintf(buffer, "VLDB: vldb size for attributes exceeded\n");
break;
case VL_BADENTRY:
sprintf(buffer, "VLDB: bad incoming vldb entry\n");
break;
case VL_BADVOLIDBUMP:
sprintf(buffer, "VLDB: illegal max volid increment\n");
break;
case VL_IDALREADYHASHED:
sprintf(buffer, "VLDB: (RO/BACK) Id already hashed\n");
break;
case VL_ENTRYLOCKED:
sprintf(buffer, "VLDB: vldb entry is already locked\n");
break;
case VL_BADVOLOPER:
sprintf(buffer, "VLDB: bad volume operation code\n");
break;
case VL_BADRELLOCKTYPE:
sprintf(buffer, "VLDB: bad release lock type\n");
break;
case VL_RERELEASE:
sprintf(buffer, "VLDB: status report: last release was aborted\n");
break;
case VL_BADSERVERFLAG:
sprintf(buffer, "VLDB: invalid replication site server flag\n");
break;
case VL_PERM:
sprintf(buffer, "VLDB: no permission access for call\n");
break;
case VOLSERREAD_DUMPERROR:
sprintf(buffer, "VOLSER: Problems encountered in reading the dump file !\n");
break;
case VOLSERDUMPERROR:
sprintf(buffer, "VOLSER: Problems encountered in doing the dump !\n");
break;
case VOLSERATTACH_ERROR:
sprintf(buffer, "VOLSER: Could not attach the volume\n");
break;
case VOLSERDETACH_ERROR:
sprintf(buffer, "VOLSER: Could not detach the volume\n");
break;
case VOLSERILLEGAL_PARTITION:
sprintf(buffer, "VOLSER: encountered illegal partition number\n");
break;
case VOLSERBAD_ACCESS:
sprintf(buffer, "VOLSER: permission denied, not a super user\n");
break;
case VOLSERVLDB_ERROR:
sprintf(buffer, "VOLSER: error detected in the VLDB\n");
break;
case VOLSERBADNAME:
sprintf(buffer, "VOLSER: error in volume name\n");
break;
case VOLSERVOLMOVED:
sprintf(buffer, "VOLSER: volume has moved\n");
break;
case VOLSERBADOP:
sprintf(buffer, "VOLSER: illegal operation\n");
break;
case VOLSERBADRELEASE:
sprintf(buffer, "VOLSER: release could not be completed\n");
break;
case VOLSERVOLBUSY:
sprintf(buffer, "VOLSER: volume is busy\n");
break;
case VOLSERNO_MEMORY:
sprintf(buffer, "VOLSER: volume server is out of memory\n");
break;
case VOLSERNOVOL:
sprintf(buffer,
"VOLSER: no such volume - location specified incorrectly or volume does not exist\n");
break;
case VOLSERMULTIRWVOL:
sprintf(buffer,
"VOLSER: multiple RW volumes with same ID, one of which should be deleted\n");
break;
case VOLSERFAILEDOP:
sprintf(buffer, "VOLSER: not all entries were successfully processed\n");
break;
usrvid, sc, scIndex);
} else {
if (info.numServers > maxservers) {
char buffer[256];
sprintf(buffer,
"%s: info.numServers=%d (> maxservers=%d)\n",
funcName, info.numServers, maxservers);
code = 1;
VSETCODE(code, buffer);
return (code);
}
for (i = 0; i < info.numServers; i++) {
serverconns[i] =
rx_NewConnection(info.hostAddr[i].sin_addr.s_addr,
info.hostAddr[i].sin_port, usrvid,
sc, scIndex);
}
}
/* Are we just setting up connections, or is this really ubik stuff? */
if (uclientp) {
*uclientp = 0;
code = ubik_ClientInit(serverconns, uclientp);
if (code) {
char buffer[256];
sprintf(buffer, "%s: ubik client init failed.\n", funcName);
VSETCODE(code, buffer);
return (code);
}
}
return 0;
}
/* copy taken from <src/volser/vsutils.c> OpenAFS-1.4.14.1 */
static afs_int32
internal_vsu_ClientInit(int noAuthFlag, const char *confDir, char *cellName, afs_int32 sauth,
struct ubik_client **uclientp, int (*secproc)())
{
return internal_ugen_ClientInit(noAuthFlag, confDir, cellName, sauth, uclientp,
secproc, "internal_vsu_ClientInit", vsu_rxkad_level,
VLDB_MAXSERVERS, AFSCONF_VLDBSERVICE, 90,
0, 0, USER_SERVICE_ID);
}
/* end of helper functions for VOS && VLDB class */
/* helper functions for VOS class: */
#ifndef OpenAFS
void vsu_SetCrypt(cryptflag)
int cryptflag;
{
if (cryptflag) {
vsu_rxkad_level = rxkad_crypt;
}
else {
vsu_rxkad_level = rxkad_auth;
}
}
#endif
int32 GetVolumeInfo(volid, server, part, voltype, rentry)
afs_int32 volid, *server, *part, *voltype;
register struct nvldbentry *rentry;
{
afs_int32 vcode;
int i, index = -1;
vcode = VLDB_GetEntryByID(volid, -1, rentry);
if (vcode) {
char buffer[256];
sprintf(buffer, "Could not fetch the entry for volume %u from VLDB \n", volid);
VSETCODE(vcode, buffer);
return (vcode);
}
MapHostToNetwork(rentry);
if (volid == rentry->volumeId[ROVOL]) {
*voltype = ROVOL;
for (i = 0; i < rentry->nServers; i++) {
if ((index == -1) && (rentry->serverFlags[i] & ITSROVOL) &&
!(rentry->serverFlags[i] & RO_DONTUSE))
index = i;
}
if (index == -1) {
char buffer[256];
sprintf(buffer, "RO volume is not found in VLDB entry for volume %u\n",
volid);
VSETCODE(-1, buffer);
return -1;
}
*server = rentry->serverNumber[index];
*part = rentry->serverPartition[index];
return 0;
}
index = Lp_GetRwIndex(rentry);
if (index == -1) {
char buffer[256];
sprintf(buffer, "RW Volume is not found in VLDB entry for volume %u\n", volid);
VSETCODE(-1, buffer);
return -1;
}
if (volid == rentry->volumeId[RWVOL]) {
*voltype = RWVOL;
*server = rentry->serverNumber[index];
*part = rentry->serverPartition[index];
return 0;
}
if (volid == rentry->volumeId[BACKVOL]) {
*voltype = BACKVOL;
*server = rentry->serverNumber[index];
*part = rentry->serverPartition[index];
return 0;
}
/* should never reach this ? */
printf("FIXME: reached end of control at %d\n",__LINE__);
return -1;
}
static int VolNameOK(name)
char *name;
{
int total;
total = strlen(name);
if (!strcmp(&name[total - 9], ".readonly")) {
return 0;
}
else if (!strcmp(&name[total - 7], ".backup")) {
return 0;
}
else {
return 1;
}
}
static int IsNumeric(name)
char *name;
{
int result, len, i;
char *ptr;
result = 1;
ptr = name;
len = strlen(name);
for (i = 0; i < len; i++) {
if (*ptr < '0' || *ptr > '9') {
result = 0;
break;
}
ptr++;
}
return result;
}
int IsPartValid(partId, server, code)
afs_int32 server, partId, *code;
{
struct partList dummyPartList;
int i, success, cnt;
success = 0;
*code = 0;
*code = UV_ListPartitions(server, &dummyPartList, &cnt);
if (*code)
ahead->next = elem;
ahead->count++;
return;
}
/* Kann vielleicht ganz raus ??? */
/* static void qGet(ahead, volid) */
/* struct tqHead *ahead; */
/* afs_int32 *volid; */
/* { */
/* struct tqElem *tmp; */
/* if (ahead->count <= 0) */
/* return; */
/* *volid = ahead->next->volid; */
/* tmp = ahead->next; */
/* ahead->next = tmp->next; */
/* ahead->count--; */
/* free(tmp); */
/* return; */
/* } */
static int FileExists(filename)
char *filename;
{
usd_handle_t ufd;
int code;
afs_hyper_t size;
code = usd_Open(filename, USD_OPEN_RDONLY, 0, &ufd);
if (code) {
return 0;
}
code = USD_IOCTL(ufd, USD_IOCTL_GETSIZE, &size);
USD_CLOSE(ufd);
if (code) {
return 0;
}
return 1;
}
static void myDisplayFormat(vol, pntr, server, part, totalOK, totalNotOK, totalBusy, fast)
HV *vol;
volintInfo *pntr;
afs_int32 server, part;
int *totalOK, *totalNotOK, *totalBusy;
int fast;
{
char pname[10];
char hostname[256];
if (fast) {
safe_hv_store(vol, "volid", 5, newSViv(pntr->volid), 0);
}
else {
safe_hv_store(vol, "status", 6, newSViv(pntr->status), 0);
safe_hv_store(vol, "volid", 5, newSViv(pntr->volid), 0);
if (pntr->status == VOK) {
safe_hv_store(vol, "name", 4, newSVpv(pntr->name, strlen((char *) pntr->name)), 0);
if (pntr->type == 0)
safe_hv_store(vol, "type", 4, newSVpv("RW", 2), 0);
if (pntr->type == 1)
safe_hv_store(vol, "type", 4, newSVpv("RO", 2), 0);
if (pntr->type == 2)
safe_hv_store(vol, "type", 4, newSVpv("BK", 2), 0);
safe_hv_store(vol, "size", 4, newSViv(pntr->size), 0);
if (pntr->inUse == 1) {
safe_hv_store(vol, "inUse", 5, newSVpv("On-line", 7), 0);
*totalOK += 1;
}
else {
safe_hv_store(vol, "inUse", 5, newSVpv("Off-line", 8), 0);
*totalNotOK += 1;
}
MapPartIdIntoName(part, pname);
strcpy(hostname, (char *) hostutil_GetNameByINet(server));
safe_hv_store(vol, "server", 6, newSVpv(hostname, strlen((char *) hostname)), 0);
safe_hv_store(vol, "backupID", 8, newSViv(pntr->backupID), 0);
safe_hv_store(vol, "parentID", 8, newSViv(pntr->parentID), 0);
safe_hv_store(vol, "cloneID", 7, newSViv(pntr->cloneID), 0);
safe_hv_store(vol, "maxquota", 8, newSViv(pntr->maxquota), 0);
safe_hv_store(vol, "creationDate", 12, newSViv(pntr->creationDate), 0);
#ifdef OpenAFS /* copy taken from <src/volser/vos.c> OpenAFS-1.2.11 FULL_LISTVOL_SWITCH*/
safe_hv_store(vol, "copyDate", 8, newSViv(pntr->copyDate), 0);
if (!pntr->backupDate)
safe_hv_store(vol, "backupDate", 10, newSVpv("Never", 5), 0);
else
safe_hv_store(vol, "backupDate", 10, newSViv(pntr->backupDate), 0);
if (pntr->accessDate)
safe_hv_store(vol, "accessDate", 10, newSViv(pntr->accessDate), 0);
#endif
if (!pntr->updateDate)
safe_hv_store(vol, "updateDate", 10, newSVpv("Never", 5), 0);
else
safe_hv_store(vol, "updateDate", 10, newSViv(pntr->updateDate), 0);
safe_hv_store(vol, "dayUse", 6, newSViv(pntr->dayUse), 0);
}
else if (pntr->status == VBUSY) {
*totalBusy += 1;
qPut(&busyHead, pntr->volid);
}
else {
*totalNotOK += 1;
qPut(¬okHead, pntr->volid);
}
}
}
static void myXDisplayFormat(stats, a_xInfoP, a_servID, a_partID, a_totalOKP,
a_totalNotOKP, a_totalBusyP)
HV *stats;
volintXInfo *a_xInfoP;
afs_int32 a_servID;
afs_int32 a_partID;
int *a_totalOKP;
int *a_totalNotOKP;
int *a_totalBusyP;
{ /*XDisplayFormat */
char hostname[256];
char pname[10];
HV *stat1 = (HV *) sv_2mortal((SV *) newHV());
HV *stat2 = (HV *) sv_2mortal((SV *) newHV());
HV *stat3 = (HV *) sv_2mortal((SV *) newHV());
HV *stat4 = (HV *) sv_2mortal((SV *) newHV());
HV *stat5 = (HV *) sv_2mortal((SV *) newHV());
HV *stat6 = (HV *) sv_2mortal((SV *) newHV());
HV *stat7 = (HV *) sv_2mortal((SV *) newHV());
HV *stat8 = (HV *) sv_2mortal((SV *) newHV());
/* Fully-detailed listing. */
safe_hv_store(stats, "status", 6, newSViv(a_xInfoP->status), 0);
safe_hv_store(stats, "volid", 5, newSViv(a_xInfoP->volid), 0);
if (a_xInfoP->status == VOK) {
/* Volume's status is OK - all the fields are valid. */
if (a_xInfoP->type == 0)
safe_hv_store(stats, "type", 4, newSVpv("RW", 2), 0);
if (a_xInfoP->type == 1)
safe_hv_store(stats, "type", 4, newSVpv("RO", 2), 0);
if (a_xInfoP->type == 2)
safe_hv_store(stats, "type", 4, newSVpv("BK", 2), 0);
safe_hv_store(stats, "size", 4, newSViv(a_xInfoP->size), 0);
safe_hv_store(stats, "filecount", 9, newSViv(a_xInfoP->filecount), 0);
if (a_xInfoP->inUse == 1) {
safe_hv_store(stats, "inUse", 5, newSVpv("On-line", 7), 0);
(*a_totalOKP)++;
}
else {
safe_hv_store(stats, "inUse", 5, newSVpv("Off-line", 8), 0);
(*a_totalNotOKP)++;
}
MapPartIdIntoName(a_partID, pname);
strcpy(hostname, (char *) hostutil_GetNameByINet(a_servID));
safe_hv_store(stats, "server", 6, newSVpv(hostname, strlen((char *) hostname)), 0);
safe_hv_store(stats, "partition", 9, newSVpv(pname, strlen(pname)), 0);
safe_hv_store(stats, "parentID", 8, newSViv(a_xInfoP->parentID), 0);
safe_hv_store(stats, "cloneID", 7, newSViv(a_xInfoP->cloneID), 0);
safe_hv_store(stats, "backupID", 8, newSViv(a_xInfoP->backupID), 0);
safe_hv_store(stats, "maxquota", 8, newSViv(a_xInfoP->maxquota), 0);
safe_hv_store(stats, "creationDate", 12, newSViv(a_xInfoP->creationDate), 0);
#ifdef OpenAFS /* copy taken from <src/volser/vos.c> OpenAFS-1.2.11 FULL_LISTVOL_SWITCH*/
safe_hv_store(stats, "copyDate", 8, newSViv(a_xInfoP->copyDate), 0);
if (!a_xInfoP->backupDate)
safe_hv_store(stats, "backupDate", 10, newSVpv("Never", 5), 0);
else
safe_hv_store(stats, "backupDate", 10, newSViv(a_xInfoP->backupDate), 0);
if (a_xInfoP->accessDate)
safe_hv_store(stats, "accessDate", 10, newSViv(a_xInfoP->accessDate), 0);
#endif
if (!a_xInfoP->updateDate) {
safe_hv_store(stats, "updateDate", 10, newSVpv("Never", 5), 0);
}
else {
safe_hv_store(stats, "updateDate", 10, newSViv(a_xInfoP->updateDate), 0);
}
safe_hv_store(stats, "dayUse", 6, newSViv(a_xInfoP->dayUse), 0);
safe_hv_store(stat1, "samenet", 7,
newSViv(a_xInfoP->stat_reads[VOLINT_STATS_SAME_NET]), 0);
safe_hv_store(stat1, "samenetauth", 11,
newSViv(a_xInfoP->stat_reads[VOLINT_STATS_SAME_NET_AUTH]), 0);
safe_hv_store(stat1, "diffnet", 7,
newSViv(a_xInfoP->stat_reads[VOLINT_STATS_DIFF_NET]), 0);
safe_hv_store(stat1, "diffnetauth", 11,
newSViv(a_xInfoP->stat_reads[VOLINT_STATS_DIFF_NET_AUTH]), 0);
safe_hv_store(stats, "Reads", 5, newRV_inc((SV *) (stat1)), 0);
safe_hv_store(stat2, "samenet", 7,
newSViv(a_xInfoP->stat_writes[VOLINT_STATS_SAME_NET]), 0);
safe_hv_store(stat2, "samenetauth", 11,
newSViv(a_xInfoP->stat_writes[VOLINT_STATS_SAME_NET_AUTH]), 0);
safe_hv_store(stat2, "diffnet", 7,
newSViv(a_xInfoP->stat_writes[VOLINT_STATS_DIFF_NET]), 0);
safe_hv_store(stat2, "diffnetauth", 11,
newSViv(a_xInfoP->stat_writes[VOLINT_STATS_DIFF_NET_AUTH]), 0);
safe_hv_store(stats, "Writes", 6, newRV_inc((SV *) (stat2)), 0);
safe_hv_store(stat3, "fileSameAuthor", 12,
safe_hv_store(stat4, "fileSameAuthor", 12,
newSViv(a_xInfoP->stat_fileSameAuthor[VOLINT_STATS_TIME_IDX_1]), 0);
safe_hv_store(stat4, "fileDiffAuthor", 12,
newSViv(a_xInfoP->stat_fileDiffAuthor[VOLINT_STATS_TIME_IDX_1]), 0);
safe_hv_store(stat4, "dirSameAuthor", 11,
newSViv(a_xInfoP->stat_dirSameAuthor[VOLINT_STATS_TIME_IDX_1]), 0);
safe_hv_store(stat4, "dirDiffAuthor", 11,
newSViv(a_xInfoP->stat_dirDiffAuthor[VOLINT_STATS_TIME_IDX_1]), 0);
safe_hv_store(stats, "1-10min", 7, newRV_inc((SV *) (stat4)), 0);
safe_hv_store(stat5, "fileSameAuthor", 12,
newSViv(a_xInfoP->stat_fileSameAuthor[VOLINT_STATS_TIME_IDX_2]), 0);
safe_hv_store(stat5, "fileDiffAuthor", 12,
newSViv(a_xInfoP->stat_fileDiffAuthor[VOLINT_STATS_TIME_IDX_2]), 0);
safe_hv_store(stat5, "dirSameAuthor", 11,
newSViv(a_xInfoP->stat_dirSameAuthor[VOLINT_STATS_TIME_IDX_2]), 0);
safe_hv_store(stat5, "dirDiffAuthor", 11,
newSViv(a_xInfoP->stat_dirDiffAuthor[VOLINT_STATS_TIME_IDX_2]), 0);
safe_hv_store(stats, "10min-1hr", 9, newRV_inc((SV *) (stat5)), 0);
safe_hv_store(stat6, "fileSameAuthor", 12,
newSViv(a_xInfoP->stat_fileSameAuthor[VOLINT_STATS_TIME_IDX_3]), 0);
safe_hv_store(stat6, "fileDiffAuthor", 12,
newSViv(a_xInfoP->stat_fileDiffAuthor[VOLINT_STATS_TIME_IDX_3]), 0);
safe_hv_store(stat6, "dirSameAuthor", 11,
newSViv(a_xInfoP->stat_dirSameAuthor[VOLINT_STATS_TIME_IDX_3]), 0);
safe_hv_store(stat6, "dirDiffAuthor", 11,
newSViv(a_xInfoP->stat_dirDiffAuthor[VOLINT_STATS_TIME_IDX_3]), 0);
safe_hv_store(stats, "1hr-1day", 8, newRV_inc((SV *) (stat6)), 0);
safe_hv_store(stat7, "fileSameAuthor", 12,
newSViv(a_xInfoP->stat_fileSameAuthor[VOLINT_STATS_TIME_IDX_4]), 0);
safe_hv_store(stat7, "fileDiffAuthor", 12,
newSViv(a_xInfoP->stat_fileDiffAuthor[VOLINT_STATS_TIME_IDX_4]), 0);
safe_hv_store(stat7, "dirSameAuthor", 11,
newSViv(a_xInfoP->stat_dirSameAuthor[VOLINT_STATS_TIME_IDX_4]), 0);
safe_hv_store(stat7, "dirDiffAuthor", 11,
newSViv(a_xInfoP->stat_dirDiffAuthor[VOLINT_STATS_TIME_IDX_4]), 0);
safe_hv_store(stats, "1day-1wk", 8, newRV_inc((SV *) (stat7)), 0);
safe_hv_store(stat8, "fileSameAuthor", 12,
newSViv(a_xInfoP->stat_fileSameAuthor[VOLINT_STATS_TIME_IDX_5]), 0);
safe_hv_store(stat8, "fileDiffAuthor", 12,
newSViv(a_xInfoP->stat_fileDiffAuthor[VOLINT_STATS_TIME_IDX_5]), 0);
safe_hv_store(stat8, "dirSameAuthor", 11,
newSViv(a_xInfoP->stat_dirSameAuthor[VOLINT_STATS_TIME_IDX_5]), 0);
safe_hv_store(stat8, "dirDiffAuthor", 11,
newSViv(a_xInfoP->stat_dirDiffAuthor[VOLINT_STATS_TIME_IDX_5]), 0);
safe_hv_store(stats, ">1wk", 4, newRV_inc((SV *) (stat8)), 0);
} /*Volume status OK */
else if (a_xInfoP->status == VBUSY) {
(*a_totalBusyP)++;
qPut(&busyHead, a_xInfoP->volid);
} /*Busy volume */
else {
(*a_totalNotOKP)++;
qPut(¬okHead, a_xInfoP->volid);
} /*Screwed volume */
} /*myXDisplayFormat */
static void VolumeStats(volinfo, pntr, entry, server, part, voltype)
HV *volinfo;
volintInfo *pntr;
struct nvldbentry *entry;
int voltype;
afs_int32 server, part;
{
int totalOK, totalNotOK, totalBusy;
myDisplayFormat(volinfo, pntr, server, part, &totalOK, &totalNotOK, &totalBusy, 0);
return;
}
static void DisplayVolumes(partition, server, part, pntr, count, fast)
HV *partition;
afs_int32 server, part;
volintInfo *pntr;
afs_int32 count, fast;
{
int totalOK, totalNotOK, totalBusy, i;
char buff[32];
totalOK = 0;
totalNotOK = 0;
totalBusy = 0;
qInit(&busyHead);
qInit(¬okHead);
for (i = 0; i < count; i++) {
HV *vol = (HV *) sv_2mortal((SV *) newHV());
myDisplayFormat(vol, pntr, server, part, &totalOK, &totalNotOK, &totalBusy, fast);
if (pntr->status == VOK) {
safe_hv_store(partition, pntr->name, strlen(pntr->name), newRV_inc((SV *) (vol)), 0);
}
else if (pntr->status == VBUSY) {
sprintf(buff, "volume_busy_%d", i);
safe_hv_store(partition, buff, strlen(buff), newRV_inc((SV *) (vol)), 0);
/* fprintf(STDERR, "DEBUG-1: %s %d\n", buff, strlen(buff)); */
}
else {
sprintf(buff, "volume_notok_%d", i);
safe_hv_store(partition, buff, strlen(buff), newRV_inc((SV *) (vol)), 0);
/* fprintf(STDERR, "DEBUG-2: %s %d\n", buff, strlen(buff)); */
}
pntr++;
}
if (!fast) {
safe_hv_store(partition, " totalOK", 8, newSViv(totalOK), 0);
safe_hv_store(partition, " totalBusy", 10, newSViv(totalBusy), 0);
safe_hv_store(partition, " totalNotOK", 11, newSViv(totalNotOK), 0);
}
}
static void XDisplayVolumes(part, a_servID, a_partID, a_xInfoP, a_count)
HV *part;
afs_int32 a_servID;
afs_int32 a_partID;
volintXInfo *a_xInfoP;
afs_int32 a_count;
{ /*XDisplayVolumes */
int totalOK; /*Total OK volumes */
int totalNotOK; /*Total screwed volumes */
int totalBusy; /*Total busy volumes */
int i; /*Loop variable */
}
else if (a_xInfoP->status == VBUSY) {
sprintf(buff, "volume_busy_%d", i);
safe_hv_store(part, buff, strlen(buff), newRV_inc((SV *) (vol)), 0);
/* fprintf(STDERR, "DEBUG-1: %s %d\n", buff, strlen(buff)); */
}
else {
sprintf(buff, "volume_notok_%d", i);
safe_hv_store(part, buff, strlen(buff), newRV_inc((SV *) (vol)), 0);
/* fprintf(STDERR, "DEBUG-2: %s %d\n", buff, strlen(buff)); */
}
a_xInfoP++;
}
/* If any volumes were found to be busy or screwed, display them.*/
safe_hv_store(part, " totalOK", 8, newSViv(totalOK), 0);
safe_hv_store(part, " totalBusy", 10, newSViv(totalBusy), 0);
safe_hv_store(part, " totalNotOK", 11, newSViv(totalNotOK), 0);
} /*XDisplayVolumes */
/* end of helper functions for VOS class */
/* helper functions for VLDB class: */
void myEnumerateEntry(stats, entry)
HV *stats;
struct nvldbentry *entry;
{
int i;
char pname[10];
char hostname[256];
int isMixed = 0;
AV *av = (AV *) sv_2mortal((SV *) newAV());
if (entry->flags & RW_EXISTS)
safe_hv_store(stats, "RWrite", 6, newSViv(entry->volumeId[RWVOL]), 0);
if (entry->flags & RO_EXISTS)
safe_hv_store(stats, "ROnly", 5, newSViv(entry->volumeId[ROVOL]), 0);
if (entry->flags & BACK_EXISTS)
safe_hv_store(stats, "Backup", 6, newSViv(entry->volumeId[BACKVOL]), 0);
if ((entry->cloneId != 0) && (entry->flags & RO_EXISTS))
safe_hv_store(stats, "cloneId", 7, newSViv(entry->cloneId), 0);
safe_hv_store(stats, "nServers", 8, newSViv(entry->nServers), 0);
for (i = 0; i < entry->nServers; i++) {
if (entry->serverFlags[i] & NEW_REPSITE)
isMixed = 1;
}
for (i = 0; i < entry->nServers; i++) {
HV *server = (HV *) sv_2mortal((SV *) newHV());
MapPartIdIntoName(entry->serverPartition[i], pname);
strcpy(hostname, (char *) hostutil_GetNameByINet(entry->serverNumber[i]));
safe_hv_store(server, "name", 4, newSVpv(hostname, strlen((char *) hostname)), 0);
safe_hv_store(server, "partition", 9, newSVpv(pname, strlen((char *) pname)), 0);
safe_hv_store(server, "serverFlags", 11, newSViv(entry->serverFlags[i]), 0);
if (entry->serverFlags[i] & ITSRWVOL)
safe_hv_store(server, "type", 4, newSVpv("RW", 2), 0);
else
safe_hv_store(server, "type", 4, newSVpv("RO", 2), 0);
if (isMixed) {
if (entry->serverFlags[i] & NEW_REPSITE)
safe_hv_store(server, "release", 7, newSVpv("New release", 11), 0);
else
safe_hv_store(server, "release", 7, newSVpv("Old release", 11), 0);
}
else {
if (entry->serverFlags[i] & RO_DONTUSE)
safe_hv_store(server, "release", 7, newSVpv("Not released", 12), 0);
}
av_push(av, newRV_inc((SV *) (server)));
}
safe_hv_store(stats, "server", 6, newRV_inc((SV *) (av)), 0);
safe_hv_store(stats, "flags", 5, newSViv(entry->flags), 0);
if (entry->flags & VLOP_ALLOPERS)
safe_hv_store(stats, "locked", 6, newSViv(entry->flags & VLOP_ALLOPERS), 0);
return;
}
static int VolumeInfoCmd(stats, name)
HV *stats;
char *name;
{
struct nvldbentry entry;
afs_int32 vcode;
/* printf("DEBUG-1-VolumeInfoCmd %s \n", name); */
/* The vlserver will handle names with the .readonly
* and .backup extension as well as volume ids.
*/
vcode = VLDB_GetEntryByName(name, &entry);
/* printf("DEBUG-2-VolumeInfoCmd %d \n", vcode); */
if (vcode)
return (vcode);
/* printf("DEBUG-3-VolumeInfoCmd \n"); */
MapHostToNetwork(&entry);
/* printf("DEBUG-4-VolumeInfoCmd \n"); */
myEnumerateEntry(stats, &entry);
/* printf("DEBUG-5-VolumeInfoCmd \n"); */
return 0;
}
/* static void PostVolumeStats_ZZZ(volinfo, entry) */
/* HV *volinfo; */
/* struct nvldbentry *entry; */
/* { */
/* myEnumerateEntry(volinfo, entry); */
/* /\* Check for VLOP_ALLOPERS *\/ */
/* if (entry->flags & VLOP_ALLOPERS) */
/* fprintf(STDOUT, " Volume is currently LOCKED \n"); */
/* return; */
/* } */
static void myprint_addrs(addr, addrs, m_uuid, nentries, print, noresolve)
HV * addr;
sprintf(buffer,
"AFS::VLDB: could not list the multi-homed server addresses\n");
VSETCODE(vcode, buffer);
}
/* Print the list */
m_addrp = (afs_int32 *) m_addrs.bulkaddrs_val;
for (j = 0; j < m_nentries; j++, m_addrp++) {
*m_addrp = htonl(*m_addrp);
#ifdef OpenAFS
if (noresolve) {
char hoststr[16];
sprintf(buf, "%s", afs_inet_ntoa_r(*m_addrp, hoststr));
av_push(IPs, newSVpv(buf, strlen(buf)));
}
else {
#endif
sprintf(buf, "%s", (char *) hostutil_GetNameByINet(*m_addrp));
av_push(names, newSVpv(buf, strlen(buf)));
#ifdef OpenAFS
}
#endif
} /* for loop */
if (j == 0) {
printf("<unknown>\n");
av_push(names, newSVpv(NULL, 0));
av_push(IPs, newSVpv(NULL, 0));
}
continue;
safe_hv_store(addr, "IP", 2, newRV_inc((SV *) (IPs)), 0);
safe_hv_store(addr, "name", 4, newRV_inc((SV *) (names)), 0);
}
}
/* Otherwise, it is a non-multihomed entry and contains
* the IP address of the server - print it.
*/
*addrp = htonl(*addrp);
#ifdef OpenAFS
if (noresolve) {
char hoststr[16];
sprintf(key, "IP-%d", j);
sprintf(buf, "%s", afs_inet_ntoa_r(*addrp, hoststr));
safe_hv_store(addr, key, 4, newSVpv(buf, strlen(buf)), 0);
}
else {
#endif
sprintf(key, "name-%d", j);
sprintf(buf, "%s", (char *) hostutil_GetNameByINet(*addrp));
safe_hv_store(addr, key, 6, newSVpv(buf, strlen(buf)), 0);
#ifdef OpenAFS
}
#endif
} /* for loop */
return;
}
static void GetServerAndPart(entry, voltype, server, part, previdx)
struct nvldbentry *entry;
afs_int32 *server, *part;
int voltype;
int *previdx;
{
int i, istart, vtype;
*server = -1;
*part = -1;
/* Doesn't check for non-existance of backup volume */
if ((voltype == RWVOL) || (voltype == BACKVOL)) {
vtype = ITSRWVOL;
istart = 0; /* seach the entire entry */
}
else {
vtype = ITSROVOL;
/* Seach from beginning of entry or pick up where we left off */
istart = ((*previdx < 0) ? 0 : *previdx + 1);
}
for (i = istart; i < entry->nServers; i++) {
if (entry->serverFlags[i] & vtype) {
*server = entry->serverNumber[i];
*part = entry->serverPartition[i];
*previdx = i;
return;
}
}
/* Didn't find any, return -1 */
*previdx = -1;
return;
}
/* end of helper functions for VLDB class */
/* helper functions for BOS class */
#ifndef OpenAFS
/* is this a digit or a digit-like thing? */
static int ismeta(ac, abase)
register int abase;
register int ac;
{
/* if (ac == '-' || ac == 'x' || ac == 'X') return 1; */
if (ac >= '0' && ac <= '7')
return 1;
if (abase <= 8)
return 0;
if (ac >= '8' && ac <= '9')
return 1;
if (abase <= 10)
return 0;
if (ac >= 'a' && ac <= 'f')
return 1;
if (ac >= 'A' && ac <= 'F')
return 1;
return 0;
}
/* given that this is a digit or a digit-like thing, compute its value */
static int getmeta(ac)
register int ac;
{
if (ac >= '0' && ac <= '9')
return ac - '0';
if (ac >= 'a' && ac <= 'f')
return ac - 'a' + 10;
if (ac >= 'A' && ac <= 'F')
return ac - 'A' + 10;
return 0;
}
afs_uint32 GetUInt32(as, aval)
register char *as;
afs_uint32 *aval;
{
register afs_uint32 total;
register int tc;
int base;
sc[2] = (struct rx_securityClass *)
rxkad_NewClientSecurityObject
(encryptLevel, &ttoken.sessionKey,
ttoken.kvno, ttoken.ticketLen, ttoken.ticket);
scIndex = 2;
}
else
fprintf(stderr, "AFS::BOS %d (getting tickets)", *code);
}
if ((scIndex == 0) || (sc[scIndex] == 0)) {
fprintf(stderr, "AFS::BOS: running unauthenticated\n");
scIndex = 0;
}
}
tconn = rx_NewConnection(addr, htons(AFSCONF_NANNYPORT), 1, sc[scIndex], scIndex);
if (!tconn) {
char buffer[256];
sprintf(buffer, "AFS::BOS: could not create rx connection\n");
*code = -1;
BSETCODE(code, buffer);
/* printf("bos DEBUG-7\n"); */
return NULL;
}
rxs_Release(sc[scIndex]);
return tconn;
}
static int DoStat(stats, aname, aconn, aint32p, firstTime)
HV *stats;
IN char *aname;
IN register struct rx_connection *aconn;
IN int aint32p;
IN int firstTime; /* true iff first instance in cmd */
{
afs_int32 temp;
char buffer[500];
register afs_int32 code;
register afs_int32 i;
struct bozo_status istatus;
char *tp;
char *is1, *is2, *is3, *is4; /* instance strings */
char info[255];
tp = buffer;
code = BOZO_GetInstanceInfo(aconn, aname, &tp, &istatus);
if (code) {
char buf[256];
sprintf(buf, "AFS::BOS: failed to get instance info for '%s' (%s)\n",
aname, em(code));
BSETCODE(code, buf);
return -1;
}
if (firstTime && aint32p && (istatus.flags & BOZO_BADDIRACCESS)) {
char buf[256];
sprintf(buf, "Bosserver reports inappropriate access on server directories\n");
BSETCODE(-1, buf);
}
/*printf("Instance %s, ", aname); */
if (aint32p) {
/* printf("(type is %s) ", buffer); */
safe_hv_store(stats, "type", 4, newSVpv(buffer, strlen(buffer)), 0);
}
sprintf(info, "%s", "");
if (istatus.fileGoal == istatus.goal) {
if (!istatus.goal)
sprintf(info, "%s", "disabled");
}
else {
if (istatus.fileGoal)
sprintf(info, "%s", "temporarily disabled");
else
sprintf(info, "%s", "temporarily enabled");
}
safe_hv_store(stats, "info", 4, newSVpv(info, strlen(info)), 0);
safe_hv_store(stats, "goal", 4, newSViv(istatus.goal), 0);
safe_hv_store(stats, "fileGoal", 8, newSViv(istatus.fileGoal), 0);
if (istatus.flags & BOZO_ERRORSTOP) {
/* printf("stopped for too many errors, "); */
safe_hv_store(stats, "status", 6, newSViv(BOZO_ERRORSTOP), 0);
}
if (istatus.flags & BOZO_HASCORE) {
/* printf("has core file, "); */
safe_hv_store(stats, "status", 6, newSViv(BOZO_HASCORE), 0);
}
safe_hv_store(stats, "flags", 5, newSViv(istatus.flags), 0);
tp = buffer;
code = BOZO_GetStatus(aconn, aname, &temp, &tp);
if (code) {
char buf[256];
sprintf(buf, "AFS::BOS: failed to get status for instance '%s' (%s)\n",
aname, em(code));
BSETCODE(code, buf);
}
else {
/* printf("currently ", aname); */
/* if (temp == BSTAT_NORMAL) printf("running normally.\n"); */
/* else if (temp == BSTAT_SHUTDOWN) printf("shutdown.\n"); */
/* else if (temp == BSTAT_STARTINGUP) printf("starting up.\n"); */
/* else if (temp == BSTAT_SHUTTINGDOWN) printf("shutting down.\n"); */
safe_hv_store(stats, "status", 6, newSViv(temp), 0);
if (buffer[0] != 0) {
/* printf(" Auxiliary status is: %s.\n", buffer); */
safe_hv_store(stats, "aux_status", 10, newSVpv(buffer, strlen(buffer)), 0);
}
}
/* are we done yet? */
if (!aint32p)
return 0;
if (istatus.procStartTime) {
/* printf(" Process last started at %s (%d proc starts)\n", */
/* DateOf(istatus.procStartTime), istatus.procStarts); */
safe_hv_store(stats, "procStartTime", 13, newSViv(istatus.procStartTime), 0);
safe_hv_store(stats, "procStarts", 10, newSViv(istatus.procStarts), 0);
}
if (istatus.lastAnyExit) {
/* printf(" Last exit at %s\n", DateOf(istatus.lastAnyExit)); */
safe_hv_store(stats, "lastAnyExit", 11, newSViv(istatus.lastAnyExit), 0);
}
if (istatus.lastErrorExit) {
is1 = is2 = is3 = is4 = (char *) 0;
/* printf(" Last error exit at %s, ", DateOf(istatus.lastErrorExit)); */
safe_hv_store(stats, "lastErrorExit", 13, newSViv(istatus.lastErrorExit), 0);
code = BOZO_GetInstanceStrings(aconn, aname, &is1, &is2, &is3, &is4);
/* don't complain about failing call, since could simply mean
* interface mismatch.
*/
if (code == 0) {
if (*is1 != 0) {
/* non-null instance string */
/* printf("by %s, ", is1); */
safe_hv_store(stats, "by", 2, newSVpv(is1, strlen(is1)), 0);
}
if (is1)
free(is1);
if (is2)
free(is2);
if (is3)
free(is3);
if (is4)
free(is4);
}
if (istatus.errorSignal) {
/* if (istatus.errorSignal == SIGTERM) */
/* printf("due to shutdown request\n"); */
/* else */
/* printf("due to signal %d\n", istatus.errorSignal); */
safe_hv_store(stats, "errorSignal", 11, newSViv(istatus.errorSignal), 0);
}
else {
/* printf("by exiting with code %d\n", istatus.errorCode); */
safe_hv_store(stats, "errorCode", 9, newSViv(istatus.errorCode), 0);
}
}
if (aint32p > 1) {
AV *av = (AV *) sv_2mortal((SV *) newAV());
/* try to display all the parms */
for (i = 0;; i++) {
tp = buffer;
code = BOZO_GetInstanceParm(aconn, aname, i, &tp);
if (code)
break;
/* fprintf(stderr, " Command %d is '%s'\n", i+1, buffer); */
av_push(av, newSVpv(buffer, strlen(buffer)));
}
safe_hv_store(stats, "command", 7, newRV_inc((SV *) (av)), 0);
tp = buffer;
code = BOZO_GetInstanceParm(aconn, aname, 999, &tp);
if (!code) {
/* Any type of failure is treated as not having a notifier program */
/* printf(" Notifier is '%s'\n", buffer); */
safe_hv_store(stats, "notifier", 8, newSVpv(buffer, strlen(buffer)), 0);
}
/* printf("\n"); */
}
return 0;
}
static afs_int32 GetServerGoal(aconn, aname)
char *aname;
struct rx_connection *aconn;
{
char buffer[500];
char *tp;
register afs_int32 code;
struct bozo_status istatus;
tp = buffer;
code = BOZO_GetInstanceInfo(aconn, aname, &tp, &istatus);
if (code) {
printf("AFS::BOS: failed to get instance info for '%s' (%s)\n", aname, em(code));
/* if we can't get the answer, assume its running */
return BSTAT_NORMAL;
}
if (istatus.goal == 0)
return BSTAT_SHUTDOWN;
else
return BSTAT_NORMAL;
}
#define PARMBUFFERSSIZE 32
static struct SalvageParms {
afs_int32 Optdebug;
afs_int32 Optnowrite;
afs_int32 Optforce;
afs_int32 Optoktozap;
afs_int32 Optrootfiles;
afs_int32 Optsalvagedirs;
afs_int32 Optblockreads;
afs_int32 OptListResidencies;
afs_int32 OptSalvageRemote;
afs_int32 OptSalvageArchival;
afs_int32 OptIgnoreCheck;
afs_int32 OptForceOnLine;
afs_int32 OptUseRootDirACL;
afs_int32 OptTraceBadLinkCounts;
afs_int32 OptDontAskFS;
afs_int32 OptLogLevel;
afs_int32 OptRxDebug;
afs_uint32 OptResidencies;
} mrafsParm;
static int DoSalvage(aconn, aparm1, aparm2, aoutName, showlog, parallel, atmpDir, orphans)
struct rx_connection *aconn;
char *aoutName;
char *aparm1;
char *aparm2;
afs_int32 showlog;
char *parallel;
p = "rlidwk";
else if (strcmp(p, "all") == 0)
p = "rlidwka";
else if (strcmp(p, "mail") == 0)
p = "lik";
else if (strcmp(p, "none") == 0)
p = "";
return parse_rights(p, rights);
}
static int32 parse_acl(p, ph, nh)
char *p;
HV *ph, *nh;
{
int32 pos, neg, acl;
char *facl;
char user[MAXSIZE];
if (sscanf(p, "%d", &pos) != 1)
return 0;
while (*p && *p != '\n')
p++;
if (*p == '\n')
p++;
if (sscanf(p, "%d", &neg) != 1)
return 0;
while (*p && *p != '\n')
p++;
if (*p == '\n')
p++;
while (pos--) {
if (sscanf(p, "%s %d", user, &acl) != 2)
return 0;
facl = format_rights(acl);
safe_hv_store(ph, user, strlen(user), newSVpv(facl, strlen(facl)), 0);
while (*p && *p != '\n')
p++;
if (*p == '\n')
p++;
}
while (neg--) {
if (sscanf(p, "%s %d", user, &acl) != 2)
return 0;
facl = format_rights(acl);
safe_hv_store(nh, user, strlen(user), newSVpv(facl, strlen(facl)), 0);
while (*p && *p != '\n')
p++;
if (*p == '\n')
p++;
}
return 1;
}
static int parse_volstat(stats, space)
HV *stats;
char *space;
{
struct VolumeStatus *status;
char *name, *offmsg, *motd;
char type[32];
status = (VolumeStatus *) space;
name = (char *) status + sizeof(*status);
offmsg = name + strlen(name) + 1;
motd = offmsg + strlen(offmsg) + 1;
safe_hv_store(stats, "Name", 4, newSVpv(name, strlen(name)), 0);
safe_hv_store(stats, "OffMsg", 6, newSVpv(offmsg, strlen(offmsg)), 0);
safe_hv_store(stats, "Motd", 4, newSVpv(motd, strlen(motd)), 0);
safe_hv_store(stats, "Vid", 3, newSViv(status->Vid), 0);
safe_hv_store(stats, "ParentId", 8, newSViv(status->ParentId), 0);
safe_hv_store(stats, "Online", 6, newSViv(status->Online), 0);
safe_hv_store(stats, "InService", 9, newSViv(status->InService), 0);
safe_hv_store(stats, "Blessed", 7, newSViv(status->Blessed), 0);
safe_hv_store(stats, "NeedsSalvage", 12, newSViv(status->NeedsSalvage), 0);
if (status->Type == ReadOnly)
strcpy(type, "ReadOnly");
else if (status->Type == ReadWrite)
strcpy(type, "ReadWrite");
else
sprintf(type, "%d", status->Type);
safe_hv_store(stats, "Type", 4, newSVpv(type, strlen(type)), 0);
safe_hv_store(stats, "MinQuota", 8, newSViv(status->MinQuota), 0);
safe_hv_store(stats, "MaxQuota", 8, newSViv(status->MaxQuota), 0);
safe_hv_store(stats, "BlocksInUse", 11, newSViv(status->BlocksInUse), 0);
safe_hv_store(stats, "PartBlocksAvail", 15, newSViv(status->PartBlocksAvail), 0);
safe_hv_store(stats, "PartMaxBlocks", 13, newSViv(status->PartMaxBlocks), 0);
return 1;
}
/* end of helper functions for FS class: */
/* helper functions for KAS class: */
static int parse_kaentryinfo(stats, ka)
HV *stats;
struct kaentryinfo *ka;
{
char buffer[sizeof(struct kaident)];
sprintf(buffer, "%s%s%s", ka->modification_user.name,
ka->modification_user.instance[0] ? "." : "", ka->modification_user.instance);
safe_hv_store(stats, "modification_user", 17, newSVpv(buffer, strlen(buffer)), 0);
safe_hv_store(stats, "minor_version", 13, newSViv(ka->minor_version), 0);
safe_hv_store(stats, "flags", 5, newSViv(ka->flags), 0);
safe_hv_store(stats, "user_expiration", 15, newSViv(ka->user_expiration), 0);
safe_hv_store(stats, "modification_time", 17, newSViv(ka->modification_time), 0);
safe_hv_store(stats, "change_password_time", 20, newSViv(ka->change_password_time), 0);
safe_hv_store(stats, "max_ticket_lifetime", 19, newSViv(ka->max_ticket_lifetime), 0);
safe_hv_store(stats, "key_version", 11, newSViv(ka->key_version), 0);
safe_hv_store(stats, "keyCheckSum", 11, newSVuv(ka->keyCheckSum), 0);
safe_hv_store(stats, "misc_auth_bytes", 15, newSVuv(ka->misc_auth_bytes), 0);
safe_hv_store(stats, "passwd_reuse", 12, newSViv(ka->reserved3), 0);
/* 1234567890123456789012345 */
return 1;
}
static int parse_ka_getstats(stats, dstats, kas, kad)
HV *stats;
HV *dstats;
struct kasstats *kas;
struct kadstats *kad;
{
safe_hv_store(stats, "minor_version", 13, newSViv(kas->minor_version), 0);
safe_hv_store(stats, "allocs", 6, newSViv(kas->allocs), 0);
safe_hv_store(stats, "frees", 5, newSViv(kas->frees), 0);
safe_hv_store(stats, "cpws", 4, newSViv(kas->cpws), 0);
safe_hv_store(stats, "reserved1", 9, newSViv(kas->reserved1), 0);
safe_hv_store(stats, "reserved2", 9, newSViv(kas->reserved2), 0);
safe_hv_store(stats, "reserved3", 9, newSViv(kas->reserved3), 0);
safe_hv_store(stats, "reserved4", 9, newSViv(kas->reserved4), 0);
/* dynamic stats */
safe_hv_store(dstats, "minor_version", 13, newSViv(kad->minor_version), 0);
safe_hv_store(dstats, "host", 4, newSViv(kad->host), 0);
safe_hv_store(dstats, "start_time", 10, newSViv(kad->start_time), 0);
safe_hv_store(dstats, "hashTableUtilization", 20, newSViv(kad->hashTableUtilization), 0);
safe_hv_store(dstats, "string_checks", 13, newSViv(kad->string_checks), 0);
safe_hv_store(dstats, "reserved1", 9, newSViv(kad->reserved1), 0);
safe_hv_store(dstats, "reserved2", 9, newSViv(kad->reserved2), 0);
void
fs__getacl(dir,follow=1)
char * dir
int32 follow
PPCODE:
{
struct ViceIoctl vi;
int32 code;
char space[MAXSIZE];
HV *ph, *nh;
vi.out_size = MAXSIZE;
vi.in_size = 0;
vi.out = space;
code = pioctl(dir, VIOCGETAL, &vi, follow);
SETCODE(code);
if (code == 0) {
ph = newHV();
nh = newHV();
if (parse_acl(space, ph, nh)) {
AV *acl;
acl = newAV();
av_store(acl, 0, newRV_noinc((SV *) ph));
av_store(acl, 1, newRV_noinc((SV *) nh));
EXTEND(sp, 1);
PUSHs(sv_bless(sv_2mortal(newRV_noinc((SV *) acl)), gv_stashpv("AFS::ACL", 1)));
}
else {
hv_undef(ph);
hv_undef(nh);
}
}
}
int32
fs_setacl(dir,acl,follow=1)
char * dir
SV * acl
int32 follow
CODE:
{
struct ViceIoctl vi;
int32 code;
char space[MAXSIZE];
char acls[MAXSIZE], *p;
HV *ph, *nh;
AV *object;
SV **sv;
HE *he;
int plen, nlen;
int32 rights;
char *name, *perm;
if (sv_isa(acl, "AFS::ACL") && SvROK(acl)
&& (SvTYPE(SvRV(acl)) == SVt_PVAV)
) {
object = (AV *) SvRV(acl);
}
else {
croak("acl is not of type AFS::ACL");
}
ph = nh = NULL;
sv = av_fetch(object, 0, 0);
if (sv) {
SV *sph = *sv;
if (SvROK(sph) && (SvTYPE(SvRV(sph)) == SVt_PVHV)) {
ph = (HV *) SvRV(sph);
}
}
sv = av_fetch(object, 1, 0);
if (sv) {
SV *snh = *sv;
if (SvROK(snh) && (SvTYPE(SvRV(snh)) == SVt_PVHV)) {
nh = (HV *) SvRV(snh);
}
}
plen = nlen = 0;
p = acls;
*p = 0;
code = 0;
if (ph) {
hv_iterinit(ph);
while ((code == 0) && (he = hv_iternext(ph))) {
I32 len;
name = hv_iterkey(he, &len);
perm = SvPV(hv_iterval(ph, he), PL_na);
code = canonical_parse_rights(perm, &rights);
if (code == 0 && rights && !name_is_numeric(name)) {
sprintf(p, "%s\t%d\n", name, rights);
p += strlen(p);
plen++;
}
}
}
if (code == 0 && nh) {
hv_iterinit(nh);
while ((code == 0) && (he = hv_iternext(nh))) {
I32 len;
name = hv_iterkey(he, &len);
perm = SvPV(hv_iterval(nh, he), PL_na);
code = canonical_parse_rights(perm, &rights);
if (code == 0 && rights && !name_is_numeric(name)) {
sprintf(p, "%s\t%d\n", name, rights);
p += strlen(p);
nlen++;
}
}
}
if (code == 0) {
sprintf(space, "%d\n%d\n%s", plen, nlen, acls);
int32
vos__DESTROY(self)
AFS::VOS self
PREINIT:
int32 code;
CODE:
{
code = ubik_ClientDestroy((struct ubik_client *) self);
/* printf("DEBUG-23 %d \n", code); */
SETCODE(code);
/* printf("DEBUG-24 \n"); */
RETVAL = (code == 0);
/* printf("DEBUG-25 \n"); */
}
OUTPUT:
RETVAL
void
vos_status(cstruct, aserver)
AFS::VOS cstruct
char *aserver
PREINIT:
afs_int32 server, code;
transDebugInfo *pntr;
afs_int32 count;
char buffer[256];
CODE:
{
server = GetServer(aserver);
if (!server) {
sprintf(buffer, "AFS::VOS: host '%s' not found in host table\n", aserver);
VSETCODE(-1, buffer);
XSRETURN_UNDEF;
}
code = UV_VolserStatus(server, &pntr, &count);
if (code) {
PrintDiagnostics("status", code);
SETCODE(1);
XSRETURN_UNDEF;
}
ST(0) = sv_newmortal();
SETCODE(0);
if (count == 0) {
sprintf(buffer, "No active transactions on %s\n", aserver);
sv_setpv(ST(0), buffer);
}
else {
sprintf(buffer, "Total transactions: %d\n", count);
sv_setpv(ST(0), buffer);
}
XSRETURN(1);
}
int32
vos_release(cstruct, name, force=Nullsv)
AFS::VOS cstruct
char *name
SV * force
PREINIT:
struct nvldbentry entry;
afs_int32 avolid, aserver, apart, vtype, code, err;
int iforce;
CODE:
{
if (!force) {
force = newSViv(0);
}
if (!SvIOKp(force)) {
char buffer[256];
sprintf(buffer, "Flag \"force\" should be numeric.\n");
VSETCODE(EINVAL, buffer);
XSRETURN_UNDEF;
}
iforce = SvIV(force);
RETVAL = 0;
avolid = vsu_GetVolumeID(name, cstruct, &err);
if (avolid == 0) {
char buffer[256];
if (err)
set_errbuff(buffer, err);
else
sprintf(buffer, "AFS::VOS: can't find volume '%s'\n", name);
VSETCODE(err ? err : ENOENT, buffer);
goto done;
}
code = GetVolumeInfo(avolid, &aserver, &apart, &vtype, &entry);
if (code) {
SETCODE(code);
goto done;
}
if (vtype != RWVOL) {
char buffer[256];
sprintf(buffer, "%s not a RW volume\n", name);
VSETCODE(ENOENT, buffer);
goto done;
}
if (!ISNAMEVALID(entry.name)) {
char buffer[256];
sprintf(buffer, "Volume name %s is too long, rename before releasing\n", entry.name);
VSETCODE(E2BIG, buffer);
goto done;
}
code = UV_ReleaseVolume(avolid, aserver, apart, iforce);
if (code) {
PrintDiagnostics("release", code);
SETCODE(code);
goto done;
}
#fprintf(STDOUT, "Released volume %s successfully\n", name);
SETCODE(0);
RETVAL = 1;
done:
;
}
OUTPUT:
RETVAL
int32
vos_create(cstruct, server, partition, name, maxquota=Nullsv, vid=Nullsv, rovid=Nullsv)
AFS::VOS cstruct
char *server
char *partition
char *name
SV * maxquota
SV * vid
SV * rovid
PREINIT:
int32 pnum;
int32 code;
struct nvldbentry entry;
int32 vcode;
int32 quota = 5000;
afs_int32 tserver;
#ifdef OpenAFS_1_4_12
afs_uint32 volid = 0, rovolid = 0, bkvolid = 0;
afs_uint32 *arovolid = NULL;
#else
afs_int32 volid = 0;
#endif
CODE:
{
if (!maxquota)
maxquota = newSViv(0);
if (!vid)
vid = newSViv(0);
if (!rovid)
rovid = newSViv(0);
if ((maxquota) && (!SvIOKp(maxquota))) {
char buffer[256];
sprintf(buffer, "Initial quota should be numeric.\n");
VSETCODE(EINVAL, buffer);
goto done;
}
quota = SvIV(maxquota);
/* printf("vos-create DEBUG-3 quota %d \n", quota); */
#ifdef OpenAFS_1_4_12
if ((vid) && (!SvIOKp(vid))) {
/* printf("vos-create DEBUG-4 vid %d \n", SvIV(vid)); */
char buffer[256];
sprintf(buffer, "Given volume ID should be numeric.\n");
VSETCODE(EINVAL, buffer);
goto done;
}
/* printf("vos-create DEBUG-5 vid %d \n", SvIV(vid)); */
volid = SvIV(vid);
/* printf("vos-create DEBUG-6 volid %d \n", volid); */
if ((rovid) && (!SvIOKp(rovid))) {
/* printf("vos-create DEBUG-7 rovid %d \n", SvIV(rovid)); */
char buffer[256];
sprintf(buffer, "Given RO volume ID should be numeric.\n");
VSETCODE(EINVAL, buffer);
goto done;
}
/* printf("vos-create DEBUG-8 rovid %d \n", SvIV(rovid)); */
arovolid = &rovolid;
rovolid = SvIV(rovid);
/* printf("vos-create DEBUG-9 rovolid %d \n", rovolid); */
if (rovolid == 0) {
arovolid = NULL;
}
code = UV_CreateVolume3(tserver, pnum, name, quota, 0, 0, 0, 0, &volid, arovolid, &bkvolid);
#else
code = UV_CreateVolume2(tserver, pnum, name, quota, 0, 0, 0, 0, &volid);
#endif
if (code) {
#PrintDiagnostics("create", code);
SETCODE(code);
goto done;
}
SETCODE(0);
RETVAL = (int32)volid;
done:
;
}
OUTPUT:
RETVAL
int32
vos_backup(cstruct, name)
AFS::VOS cstruct
char *name
PREINIT:
int32 avolid, aserver, apart, vtype, code, err;
int32 buvolid, buserver, bupart, butype;
struct nvldbentry entry;
struct nvldbentry buentry;
CODE:
{
RETVAL = 0;
avolid = vsu_GetVolumeID(name, cstruct, &err);
if (avolid == 0) {
char buffer[256];
if (err)
set_errbuff(buffer, err);
else
sprintf(buffer, "AFS::VOS: can't find volume ID or name '%s'\n", name);
VSETCODE(err ? err : ENOENT, buffer);
goto done;
}
code = GetVolumeInfo(avolid, &aserver, &apart, &vtype, &entry);
if (code) {
SETCODE(code);
goto done;
}
/* verify this is a readwrite volume */
if (vtype != RWVOL) {
char buffer[256];
sprintf(buffer, "%s not RW volume\n", name);
VSETCODE(-1, buffer);
goto done;
}
/* is there a backup volume already? */
if (entry.flags & BACK_EXISTS) {
/* yep, where is it? */
buvolid = entry.volumeId[BACKVOL];
code = GetVolumeInfo(buvolid, &buserver, &bupart, &butype, &buentry);
if (code) {
SETCODE(code);
goto done;
}
/* is it local? */
code = VLDB_IsSameAddrs(buserver, aserver, &err);
if (err) {
char buffer[256];
sprintf(buffer,
"Failed to get info about server's %d address(es) from vlserver; aborting call!\n",
buserver);
VSETCODE(err, buffer);
goto done;
}
if (!code) {
char buffer[256];
sprintf(buffer, "FATAL ERROR: backup volume %u exists on server %u\n",
buvolid, buserver);
VSETCODE(-1, buffer);
goto done;
}
}
/* nope, carry on */
code = UV_BackupVolume(aserver, apart, avolid);
if (code) {
PrintDiagnostics("backup", code);
SETCODE(0);
goto done;
}
#fprintf(STDOUT, "Created backup volume for %s \n", name);
SETCODE(0);
RETVAL = 1;
done:
;
}
OUTPUT:
RETVAL
int32
vos_remove(cstruct, name, servername=NULL, parti=NULL)
AFS::VOS cstruct
char *name
char *servername
char *parti
PREINIT:
afs_int32 err, code = 0;
afs_int32 server = 0, partition = -1, volid;
afs_int32 idx, j;
CODE:
{
RETVAL = 0;
if (servername && strlen(servername) != 0) {
server = GetServer(servername);
if (!server) {
char buffer[256];
sprintf(buffer, "AFS::VOS: server '%s' not found in host table\n", servername);
VSETCODE(ENOENT, buffer);
struct nvldbentry entry;
volintInfo info;
int32 volid;
int32 clear, code, err;
int32 aserver, apart;
int previdx = -1;
#endif
CODE:
{
#ifdef OpenAFS
if (!mquota)
mquota = newSViv(-1);
if (!clearuse)
clearuse = newSViv(0);
if ((!SvIOKp(mquota))) { /* -max <quota> */
char buffer[256];
sprintf(buffer, "invalid quota value\n");
VSETCODE(EINVAL, buffer);
goto done;
}
if ((!SvIOKp(clearuse))) { /* -clearuse */
char buffer[256];
sprintf(buffer, "flag \"clearuse\" is not an integer\n");
VSETCODE(EINVAL, buffer);
goto done;
}
/* printf("vos-setfields DEBUG-1 name %s mquota %d clearuse %d \n", name, (int)SvIV(mquota), (int)SvIV(clearuse)); */
RETVAL = 0;
volid = vsu_GetVolumeID(name, cstruct, &err); /* -id */
if (volid == 0) {
char buffer[256];
if (err)
set_errbuff(buffer, err);
else
sprintf(buffer, "Unknown volume ID or name '%s'\n", name);
VSETCODE(err ? err : -1, buffer);
goto done;
}
code = VLDB_GetEntryByID(volid, RWVOL, &entry);
if (code) {
char buffer[256];
sprintf(buffer, "Could not fetch the entry for volume number %u from VLDB \n", volid);
VSETCODE(code, buffer);
goto done;
}
MapHostToNetwork(&entry);
GetServerAndPart(&entry, RWVOL, &aserver, &apart, &previdx);
if (previdx == -1) {
char buffer[256];
sprintf(buffer, "Volume %s does not exist in VLDB\n\n", name);
VSETCODE(ENOENT, buffer);
goto done;
}
Zero(&info, 1, volintInfo);
info.volid = volid;
info.type = RWVOL;
info.creationDate = -1;
info.updateDate = -1;
info.dayUse = -1;
info.maxquota = -1;
info.flags = -1;
info.spare0 = -1;
info.spare1 = -1;
info.spare2 = -1;
info.spare3 = -1;
info.maxquota = SvIV(mquota);
clear = SvIV(clearuse);
if (clear)
info.dayUse = 0;
code = UV_SetVolumeInfo(aserver, apart, volid, &info);
if (code) {
char buffer[256];
sprintf(buffer, "Could not update volume info fields for volume number %u\n", volid);
VSETCODE(code, buffer);
}
else
SETCODE(code);
RETVAL = 1;
done:
;
#else
not_here("AFS::VOS::setfields");
#endif
}
OUTPUT:
RETVAL
int32
vos_restore(cstruct,server,partition,name,file=NULL,id=NULL,inter=Nullsv,overwrite=NULL,offline=Nullsv,readonly=Nullsv)
AFS::VOS cstruct
char *server
char *partition
char *name
char *file
char *id
SV * inter
char *overwrite
SV * offline
SV * readonly
PREINIT:
afs_int32 avolid, aparentid, aserver, apart, code, vcode, err;
afs_int32 aoverwrite = AFS_ASK;
int restoreflags, voltype = RWVOL, ireadonly = 0, ioffline = 0;
char afilename[NameLen], avolname[VOLSER_MAXVOLNAME +1];
char volname[VOLSER_MAXVOLNAME +1];
struct nvldbentry entry;
CODE:
{
aparentid = 0;
if (!inter) {
inter = newSViv(0);
}
if (!offline) {
offline = newSViv(0);
}
if (!readonly) {
readonly = newSViv(0);
}
if ((!SvIOKp(inter))) {
char buffer[256];
sprintf(buffer, "Flag \"inter\" should be numeric.\n");
VSETCODE(EINVAL, buffer);
RETVAL = 0;
goto done;
}
else
aoverwrite = AFS_ASK;
if ((!SvIOKp(offline))) {
char buffer[256];
sprintf(buffer, "Flag \"offline\" should be numeric.\n");
VSETCODE(EINVAL, buffer);
RETVAL = 0;
goto done;
}
else
ioffline = SvIV(offline);
if ((!SvIOKp(readonly))) {
char buffer[256];
sprintf(buffer, "Flag \"readonly\" should be numeric.\n");
VSETCODE(EINVAL, buffer);
RETVAL = 0;
goto done;
}
else
ireadonly = SvIV(readonly);
if (id && strlen(id) != 0) {
avolid = vsu_GetVolumeID(id, cstruct, &err);
if (avolid == 0) {
char buffer[256];
if (err)
set_errbuff(buffer, err);
else
sprintf(buffer, "AFS::VOS: can't find volume '%s'\n", id);
VSETCODE(err ? err : -1, buffer);
RETVAL = 0;
goto done;
}
}
else
avolid = 0;
if (overwrite && strlen(overwrite) != 0) {
if ((strcmp(overwrite, "a") == 0) || (strcmp(overwrite, "abort") == 0)) {
aoverwrite = AFS_ABORT;
}
else if ((strcmp(overwrite, "f") == 0) || (strcmp(overwrite, "full") == 0)) {
aoverwrite = AFS_FULL;
}
else if ((strcmp(overwrite, "i") == 0) ||
(strcmp(overwrite, "inc") == 0) ||
(strcmp(overwrite, "increment") == 0) ||
(strcmp(overwrite, "incremental") == 0)) {
aoverwrite = AFS_INC;
}
else {
char buffer[256];
sprintf(buffer, "AFS::VOS: %s is not a valid OVERWRITE argument\n",
overwrite);
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
}
if ((ireadonly))
voltype = ROVOL;
aserver = GetServer(server);
if (aserver == 0) {
char buffer[256];
sprintf(buffer, "AFS::VOS: server '%s' not found in host table\n", server);
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
apart = volutil_GetPartitionID(partition);
if (apart < 0) {
char buffer[256];
sprintf(buffer, "AFS::VOS: could not interpret partition name '%s'\n", partition);
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
if (!IsPartValid(apart, aserver, &code)) { /*check for validity of the partition */
char buffer[256];
if (code)
set_errbuff(buffer, code);
else
sprintf(buffer, "AFS::VOS: partition %s does not exist on the server\n",
partition);
VSETCODE(code ? code : -1, buffer);
RETVAL = 0;
goto done;
}
strcpy(avolname, name);
if (!ISNAMEVALID(avolname)) {
char buffer[256];
sprintf(buffer, "AFS::VOS: the name of the volume %s exceeds the size limit\n",
avolname);
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
if (!VolNameOK(avolname)) {
char buffer[256];
sprintf(buffer, "Illegal volume name %s, should not end in .readonly or .backup\n",
avolname);
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
if (file && strlen(file) != 0) {
strcpy(afilename, file);
if (!FileExists(afilename)) {
char buffer[256];
sprintf(buffer, "Can't access file %s\n", afilename);
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
}
else {
strcpy(afilename, "");
}
/* Check if volume exists or not */
vsu_ExtractName(volname, avolname);
vcode = VLDB_GetEntryByName(volname, &entry);
if (vcode) { /* no volume - do a full restore */
restoreflags = RV_FULLRST;
if ((aoverwrite == AFS_INC) || (aoverwrite == AFS_ABORT)) {
char buffer[256];
sprintf(buffer, "Volume does not exist; Will perform a full restore\n");
VSETCODE(vcode, buffer);
}
}
else if ((!ireadonly && Lp_GetRwIndex(&entry) == -1) /* RW volume does not exist - do a full */
||(ireadonly && !Lp_ROMatch(0, 0, &entry))) { /* RO volume does not exist - do a full */
restoreflags = RV_FULLRST;
if ((aoverwrite == AFS_INC) || (aoverwrite == AFS_ABORT))
fprintf(stderr, "%s Volume does not exist; Will perform a full restore\n",
ireadonly ? "RO" : "RW");
if (avolid == 0) {
avolid = entry.volumeId[voltype];
}
else if (entry.volumeId[voltype] != 0 && entry.volumeId[voltype] != avolid) {
avolid = entry.volumeId[voltype];
}
aparentid = entry.volumeId[RWVOL];
}
else { /* volume exists - do we do a full incremental or abort */
int Oserver, Opart, Otype, vol_elsewhere = 0;
struct nvldbentry Oentry;
int c, dc;
if (avolid == 0) {
avolid = entry.volumeId[voltype];
}
else if (entry.volumeId[voltype] != 0 && entry.volumeId[voltype] != avolid) {
avolid = entry.volumeId[voltype];
}
aparentid = entry.volumeId[RWVOL];
/* A file name was specified - check if volume is on another partition */
vcode = GetVolumeInfo(avolid, &Oserver, &Opart, &Otype, &Oentry);
if (vcode) {
SETCODE(0);
RETVAL = 0;
goto done;
}
vcode = VLDB_IsSameAddrs(Oserver, aserver, &err);
if (err) {
char buffer[256];
sprintf(buffer,
"Failed to get info about server's %d address(es) from vlserver (err=%d); aborting call!\n",
Oserver, err);
VSETCODE(err, buffer);
RETVAL = 0;
goto done;
}
if (!vcode || (Opart != apart))
vol_elsewhere = 1;
if (aoverwrite == AFS_ASK) {
if (strcmp(afilename, "") == 0) { /* The file is from standard in */
char buffer[256];
sprintf(buffer,
"Volume exists and no OVERWRITE argument specified; Aborting restore command\n");
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
/* Ask what to do */
if (vol_elsewhere) {
char buffer[256];
sprintf(buffer,
"The volume %s %u already exists on a different server/part\n",
volname, entry.volumeId[voltype]);
VSETCODE(-1, buffer);
fprintf(stderr, "Do you want to do a full restore or abort? [fa](a): ");
}
else {
char buffer[256];
sprintf(buffer, "The volume %s %u already exists in the VLDB\n",
volname, entry.volumeId[voltype]);
VSETCODE(-1, buffer);
fprintf(stderr,
"Do you want to do a full/incremental restore or abort? [fia](a): ");
}
dc = c = getchar();
while (!(dc == EOF || dc == '\n'))
dc = getchar(); /* goto end of line */
if ((c == 'f') || (c == 'F'))
aoverwrite = AFS_FULL;
else if ((c == 'i') || (c == 'I'))
aoverwrite = AFS_INC;
else
aoverwrite = AFS_ABORT;
}
if (aoverwrite == AFS_ABORT) {
char buffer[256];
sprintf(buffer, "Volume exists; Aborting restore command\n");
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
else if (aoverwrite == AFS_FULL) {
restoreflags = RV_FULLRST;
fprintf(stderr, "Volume exists; Will delete and perform full restore\n");
}
else if (aoverwrite == AFS_INC) {
restoreflags = 0;
if (vol_elsewhere) {
char buffer[256];
sprintf(buffer,
"%s volume %u already exists on a different server/part; not allowed\n",
ireadonly ? "RO" : "RW", avolid);
VSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
}
}
if ((ioffline))
restoreflags |= RV_OFFLINE;
if (ireadonly)
restoreflags |= RV_RDONLY;
/* restoreflags |= RV_CRNEW; */
/* restoreflags |= RV_LUDUMP; */
#ifdef OpenAFS_1_4_05
code = UV_RestoreVolume2(aserver, apart, avolid, aparentid, avolname,
restoreflags, WriteData, afilename);
#else
code = UV_RestoreVolume(aserver, apart, avolid, avolname,
restoreflags, WriteData, afilename);
#endif
if (code) {
PrintDiagnostics("restore", code);
SETCODE(code);
RETVAL = 0;
goto done;
}
SETCODE(0);
RETVAL = 1;
done:
;
}
OUTPUT:
RETVAL
int32
vos_dump(cstruct, id, time=NULL, file=NULL, server=NULL, partition=NULL, clone=Nullsv, omit=Nullsv)
AFS::VOS cstruct
char *id
char *time
char *file
char *server
char *partition
SV * clone
SV * omit
PREINIT:
afs_int32 avolid, aserver, apart, voltype, fromdate=0, code=0, err, i;
char filename[NameLen];
struct nvldbentry entry;
afs_int32 omitdirs = 0;
CODE:
{
if (!clone)
clone = newSViv(0);
if (!omit)
omit = newSViv(0);
if ((!SvIOKp(omit))) {
char buffer[256];
sprintf(buffer, "Flag \"omit\" should be numeric.\n");
VSETCODE(EINVAL, buffer);
RETVAL = 0;
goto done;
}
else
omitdirs = SvIV(omit); /* -omit */
/* printf("vos_dump DEBUG-1 clone = %d omit = %d omitdirs = %d \n", clone, omit, omitdirs); */
RETVAL = 0;
rx_SetRxDeadTime(60 * 10);
for (i = 0; i < MAXSERVERS; i++) {
struct rx_connection *rxConn = ubik_GetRPCConn((struct ubik_client *) cstruct, i);
if (rxConn == 0)
break;
rx_SetConnDeadTime(rxConn, rx_connDeadTime);
if (rxConn->service)
rxConn->service->connDeadTime = rx_connDeadTime;
}
avolid = vsu_GetVolumeID(id, cstruct, &err);
if (avolid == 0) {
char buffer[256];
if (err)
set_errbuff(buffer, err);
else
sprintf(buffer, "AFS::VOS: can't find volume '%s'\n", id);
VSETCODE(err ? err : ENOENT, buffer);
goto done;
}
if ((server && (strlen(server) != 0)) || (partition && (strlen(partition) != 0))) {
if (!(server && (strlen(server) != 0)) || !(partition && (strlen(partition) != 0))) {
char buffer[256];
sprintf(buffer, "Must specify both SERVER and PARTITION arguments\n");
VSETCODE(-1, buffer);
goto done;
}
aserver = GetServer(server);
if (aserver == 0) {
char buffer[256];
sprintf(buffer, "Invalid server name\n");
VSETCODE(-1, buffer);
goto done;
}
apart = volutil_GetPartitionID(partition);
if (apart < 0) {
char buffer[256];
sprintf(buffer, "Invalid partition name\n");
VSETCODE(-1, buffer);
goto done;
}
}
else {
code = GetVolumeInfo(avolid, &aserver, &apart, &voltype, &entry);
if (code) {
SETCODE(code);
goto done;
}
}
if (time && strcmp(time, "0")) {
code = ktime_DateToInt32(time, &fromdate);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::VOS: failed to parse date '%s' (error=%d))\n", time, code);
VSETCODE(code, buffer);
goto done;
}
}
if (file && (strlen(file) != 0)) {
strcpy(filename, file);
}
else {
strcpy(filename, "");
}
#ifdef OpenAFS_1_4_05
int iclone = 0;
retry_dump:
/* printf("vos_dump DEBUG-2 clone = %d omitdirs = %d \n", clone, omitdirs); */
if ((!SvIOKp(clone))) {
char buffer[256];
sprintf(buffer, "Flag \"clone\" should be numeric.\n");
VSETCODE(EINVAL, buffer);
RETVAL = 0;
goto done;
}
else
iclone = SvIV(clone);
if (iclone) {
/* printf("vos_dump DEBUG-2-1 clone = %d omitdirs = %d \n", clone, omitdirs); */
code = UV_DumpClonedVolume(avolid, aserver, apart, fromdate,
DumpFunction, filename, omitdirs);
} else {
/* printf("vos_dump DEBUG-2-2 clone = %d omitdirs = %d \n", clone, omitdirs); */
code = UV_DumpVolume(avolid, aserver, apart, fromdate, DumpFunction,
filename, omitdirs);
}
/* printf("vos_dump DEBUG-3 code = %d \n", code); */
if ((code == RXGEN_OPCODE) && (omitdirs)) {
omitdirs = 0;
goto retry_dump;
}
#else
/* printf("vos_dump DEBUG-4 \n"); */
code = UV_DumpVolume(avolid, aserver, apart, fromdate, DumpFunction, filename);
/* printf("vos_dump DEBUG-5 code = %d \n", code); */
#endif
if (code) {
PrintDiagnostics("dump", code);
SETCODE(code);
goto done;
}
SETCODE(0);
}
} /* process each vldb entry */
/* printf("vos-backupsys DEBUG-22: Succ %d Fail %d\n", totalBack, totalFail); */
if (arrayEntries.nbulkentries_val)
free(arrayEntries.nbulkentries_val);
SETCODE(0);
XPUSHs(sv_2mortal(newRV_inc((SV *) (av1))));
XPUSHs(sv_2mortal(newRV_inc((SV *) (av2))));
XSRETURN(2);
}
void
vos_listpart(cstruct, server)
AFS::VOS cstruct
char *server
PREINIT:
int32 aserver, code;
struct partList dummyPartList;
int i, total, cnt;
char pname[10];
PPCODE:
{
aserver = GetServer(server);
if (aserver == 0) {
char buffer[256];
sprintf(buffer, "AFS::VOS: server '%s' not found in host table\n", server);
VSETCODE(-1, buffer);
XSRETURN_UNDEF;
}
code = UV_ListPartitions(aserver, &dummyPartList, &cnt);
if (code) {
PrintDiagnostics("listpart", code);
XSRETURN_UNDEF;
}
total = 0;
for (i = 0; i < cnt; i++) {
if (dummyPartList.partFlags[i] & PARTVALID) {
Zero(pname, 10, char);
MapPartIdIntoName(dummyPartList.partId[i], pname);
XPUSHs(sv_2mortal(newSVpv(pname, strlen(pname))));
total++;
}
}
SETCODE(0);
XSRETURN(total);
}
void
vos_listvolume(cstruct, name)
AFS::VOS cstruct
char *name
PREINIT:
struct nvldbentry entry;
afs_int32 vcode = 0;
volintInfo *pntr = (volintInfo *)0;
afs_int32 volid;
afs_int32 code, err;
int voltype, foundserv = 0, foundentry = 0;
afs_int32 aserver, apart;
char apartName[10];
int previdx = -1;
HV *volinfo = (HV*)sv_2mortal((SV*)newHV());
PPCODE:
{
volid = vsu_GetVolumeID(name, cstruct, &err); /* -id */
if (volid == 0) {
char buffer[256];
if (err)
set_errbuff(buffer, err);
else
sprintf(buffer, "Unknown volume ID or name '%s'\n", name);
VSETCODE(err ? err : -1, buffer);
XSRETURN_UNDEF;
}
vcode = VLDB_GetEntryByID(volid, -1, &entry);
if (vcode) {
char buffer[256];
sprintf(buffer, "Could not fetch the entry for volume number %u from VLDB \n", volid);
VSETCODE(vcode, buffer);
XSRETURN_UNDEF;
}
MapHostToNetwork(&entry);
if (entry.volumeId[RWVOL] == volid)
voltype = RWVOL;
else if (entry.volumeId[BACKVOL] == volid)
voltype = BACKVOL;
else /* (entry.volumeId[ROVOL] == volid) */
voltype = ROVOL;
do { /* do {...} while (voltype == ROVOL) */
/* Get the entry for the volume. If its a RW vol, get the RW entry.
* It its a BK vol, get the RW entry (even if VLDB may say the BK doen't exist).
* If its a RO vol, get the next RO entry.
*/
GetServerAndPart(&entry, ((voltype == ROVOL) ? ROVOL : RWVOL), &aserver, &apart,
&previdx);
if (previdx == -1) { /* searched all entries */
if (!foundentry) {
char buffer[256];
sprintf(buffer, "Volume %s does not exist in VLDB\n\n", name);
VSETCODE(ENOENT, buffer);
XSRETURN_UNDEF;
}
break;
}
foundentry = 1;
/* Get information about the volume from the server */
code = UV_ListOneVolume(aserver, apart, volid, &pntr);
if (code) {
char buffer[256];
if (code == ENODEV) {
if ((voltype == BACKVOL) && !(entry.flags & BACK_EXISTS)) {
/* The VLDB says there is no backup volume and its not on disk */
sprintf(buffer, "Volume %s does not exist\n", name);
}
else {
sprintf(buffer,
"Volume does not exist on server %s as indicated by the VLDB\n",
hostutil_GetNameByINet(aserver));
}
}
else {
sprintf(buffer, "examine");
}
if (pntr)
free(pntr);
VSETCODE(code, buffer);
XSRETURN_UNDEF;
}
else {
foundserv = 1;
MapPartIdIntoName(apart, apartName);
/* safe_hv_store(volinfo, "name", 4, newSVpv(name, strlen((char *) name)), 0); */
safe_hv_store(volinfo, "partition", 9, newSVpv(apartName, strlen((char *) apartName)), 0);
VolumeStats(volinfo, pntr, &entry, aserver, apart, voltype);
if ((voltype == BACKVOL) && !(entry.flags & BACK_EXISTS)) {
/* The VLDB says there is no backup volume yet we found one on disk */
char buffer[256];
sprintf(buffer, "Volume %s does not exist in VLDB\n", name);
if (pntr)
free(pntr);
VSETCODE(ENOENT, buffer);
XSRETURN_UNDEF;
}
}
if (pntr)
free(pntr);
} while (voltype == ROVOL);
SETCODE(0);
ST(0) = sv_2mortal(newRV_inc((SV *) volinfo));
XSRETURN(1);
}
MODULE = AFS PACKAGE = AFS::VLDB PREFIX = vldb_
AFS::VLDB
vldb_new(class=0, verb=0, timeout=90, noauth=0, localauth=0, tcell=NULL, crypt=0)
char * class
int verb
int timeout
int noauth
int localauth
char * tcell
int crypt
PREINIT:
int32 code = -1;
extern int verbose;
PPCODE:
{
if (tcell && (tcell[0] == '\0' || tcell[0] == '0'))
tcell = NULL;
/* Initialize the ubik_client connection */
rx_SetRxDeadTime(timeout); /* timeout seconds inactivity before declared dead */
cstruct = (struct ubik_client *) 0;
verbose = verb;
if (crypt) /* -crypt specified */
vsu_SetCrypt(1);
code = internal_vsu_ClientInit((noauth != 0),
AFSDIR_CLIENT_ETC_DIRPATH, tcell, localauth,
&cstruct, UV_SetSecurity);
if (code == 0) {
ST(0) = sv_newmortal();
sv_setref_pv(ST(0), "AFS::VLDB", (void *) cstruct);
XSRETURN(1);
}
else
XSRETURN_UNDEF;
}
int32
vldb__DESTROY(self)
AFS::VLDB self
PREINIT:
int32 code = 0;
CODE:
{
code = ubik_ClientDestroy(self);
/* printf("DEBUG-23 %d \n", code); */
SETCODE(code);
/* printf("DEBUG-24 \n"); */
RETVAL = (code == 0);
/* printf("DEBUG-25 \n"); */
}
OUTPUT:
RETVAL
av = (AV *) SvRV(object);
}
else {
BSETCODE(-1, "AFS::BOS: USER not an array reference\n");
XSRETURN_UNDEF;
}
len = av_len(av);
if (len != -1) {
for (i = 0; i <= len; i++) {
sv = *av_fetch(av, i, 0);
if (sv && !SvROK(sv)) {
name = SvPV_nolen(sv);
code = BOZO_DeleteSUser(self, name);
if (code) {
char buffer[240];
sprintf(buffer, "AFS::BOS: failed to delete user");
if (code == ENOENT)
sprintf(buffer, "%s (no such user)\n", buffer);
else
sprintf(buffer, "%s (%s)\n", em(code), buffer);
BSETCODE(code, buffer);
}
}
} /* for loop */
}
RETVAL = (code == 0);
}
OUTPUT:
RETVAL
int32
bos_addkey(self, kvno, string=NULL)
AFS::BOS self
int32 kvno
char *string
PREINIT:
int32 code = 0;
struct ktc_encryptionKey tkey;
char *tcell = (char *) 0; /* use current cell */
char buf[BUFSIZ], ver[BUFSIZ];
CODE:
{
not_here("AFS::BOS::addkey");
Zero(&tkey, 1, struct ktc_encryptionKey);
RETVAL = 42;
if (string)
strcpy(buf, string);
else {
/* prompt for key */
code = des_read_pw_string(buf, sizeof(buf), "input key: ", 0);
if (code || strlen(buf) == 0) {
char buffer[256];
sprintf(buffer, "Bad key: \n");
BSETCODE(code ? code : -1, buffer);
RETVAL = 0;
}
code = des_read_pw_string(ver, sizeof(ver), "Retype input key: ", 0);
if (code || strlen(ver) == 0) {
char buffer[256];
sprintf(buffer, "Bad key: \n");
BSETCODE(code ? code : -1, buffer);
RETVAL = 0;
}
if (strcmp(ver, buf) != 0) {
char buffer[256];
sprintf(buffer, "\nInput key mismatch\n");
BSETCODE(-1, buffer);
RETVAL = 0;
}
}
if (RETVAL == 42) {
if (kvno == 999) {
/* bcrypt key */
strcpy((char *) &tkey, buf);
}
else { /* kerberos key */
ka_StringToKey(buf, tcell, &tkey);
}
code = BOZO_AddKey(self, kvno, &tkey);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to set key %d (%s)\n", kvno, em(code));
BSETCODE(code, buffer);
}
SETCODE(code);
RETVAL = (code == 0);
}
if (tcell)
free(tcell);
}
OUTPUT:
RETVAL
int32
bos_removekey(self, object)
AFS::BOS self
SV* object
PREINIT:
int32 code = 0;
int32 temp;
CODE:
{
not_here("AFS::BOS::removekey");
if (SvIOK(object)) {
temp = (int32) SvIV(object);
code = BOZO_DeleteKey(self, temp);
}
else if (SvTYPE(SvRV(object)) == SVt_PVAV) {
/* object is array ref */
int len, i;
AV *av;
SV *sv;
av = (AV *) SvIV(object);
len = av_len(av);
if (len != -1) {
for (i = 0; i <= len; i++) {
sv = *av_fetch(av, i, 0);
if (sv) {
temp = SvIV(sv);
code = BOZO_DeleteKey(self, temp);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to deletekey");
BSETCODE(code, buffer);
}
}
} /* for loop */
}
}
SETCODE(code);
RETVAL = (code == 0);
}
OUTPUT:
RETVAL
int32
bos__create(self, name, type, object, notifier=NULL)
AFS::BOS self
char *name
char *type
SV *object
char *notifier
PREINIT:
int32 i, len, code = 0;
char *parms[6];
AV *av; SV *sv;
STRLEN namelen;
CODE:
{
if (SvTYPE(SvRV(object)) != SVt_PVAV) {
code = -1;
BSETCODE(code, "AFS::BOS COMMAND not an array reference\n");
goto done;
}
for (i = 0; i < 6; i++)
parms[i] = "";
av = (AV *) SvRV(object);
len = av_len(av);
if (len != -1) {
for (i = 0; i <= len && i < 6; i++) {
sv = *av_fetch(av, i, 0);
if (sv)
parms[i] = SvPV(sv, namelen);
}
}
if (notifier == NULL)
notifier = NONOTIFIER;
code = BOZO_CreateBnode(self, type, name, parms[0], parms[1], parms[2],
parms[3], parms[4], notifier);
if (code) {
char buffer[256];
sprintf(buffer,
"AFS::BOS: failed to create new server instance %s of type '%s' (%s)\n", name,
type, em(code));
BSETCODE(code, buffer);
goto done;
}
SETCODE(code);
done:
RETVAL = (code == 0);
}
OUTPUT:
RETVAL
int32
bos__restart(self, bosserver=0, all=0, object=NULL)
AFS::BOS self
int bosserver
int all
SV *object
PREINIT:
int32 code = 0;
CODE:
{
if (bosserver) {
if (object != NULL) {
char buffer[256];
sprintf(buffer,
"AFS::BOS: can't specify both 'bosserver' and specific servers to restart.\n");
BSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
code = BOZO_ReBozo(self);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to restart bosserver (%s)\n", em(code));
BSETCODE(code, buffer);
}
RETVAL = (code == 0);
goto done;
}
if (object == NULL) {
if (all) {
code = BOZO_RestartAll(self);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to restart servers (%s)\n", em(code));
BSETCODE(code, buffer);
}
}
else {
char buffer[256];
sprintf(buffer, "AFS::BOS: To restart all processes please specify 'all'\n");
BSETCODE(-1, buffer);
}
RETVAL = (code == 0);
goto done;
}
else {
if (all) {
char buffer[256];
sprintf(buffer, "AFS::BOS: Can't use 'all' along with individual instances\n");
BSETCODE(-1, buffer);
RETVAL = 0;
goto done;
}
else {
AV *av;
SV *sv;
STRLEN namelen;
char *instance;
int i, len;
if (SvTYPE(SvRV(object)) != SVt_PVAV) {
BSETCODE(-1, "AFS::BOS: SERVER not an array reference\n");
RETVAL = 0;
goto done;
}
av = (AV *) SvRV(object);
len = av_len(av);
if (len != -1) {
for (i = 0; i <= len && i < 6; i++) {
sv = *av_fetch(av, i, 0);
if (sv) {
instance = (char *) safemalloc(BOZO_BSSIZE);
instance = SvPV(sv, namelen);
code = BOZO_Restart(self, instance);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to restart instance %s (%s)\n",
instance, em(code));
BSETCODE(code, buffer);
}
}
} /* for loop */
SETCODE(code);
RETVAL = (code == 0);
}
}
}
done:
;
}
OUTPUT:
RETVAL
int32
bos_setrestart(self, time, general=Nullsv, newbinary=Nullsv)
AFS::BOS self
char *time
SV * general
SV * newbinary
PREINIT:
int32 code = 0, count = 0;
struct ktime restartTime;
afs_int32 type;
int igeneral;
int inewbinary;
CODE:
{
if (!general) {
general = newSViv(0);
}
if (!SvIOKp(general)) {
char buffer[256];
sprintf(buffer, "AFS::BOS: Flag \"general\" should be numeric.\n");
BSETCODE(-1, buffer);
XSRETURN_UNDEF;
}
if (!newbinary) {
newbinary = newSViv(0);
}
if (!SvIOKp(newbinary)) {
char buffer[256];
sprintf(buffer, "AFS::BOS: Flag \"newbinary\" should be numeric.\n");
BSETCODE(-1, buffer);
XSRETURN_UNDEF;
}
igeneral = SvIV(general);
inewbinary = SvIV(newbinary);
if (igeneral) {
count++;
type = 1;
}
if (inewbinary) {
count++;
type = 2;
}
if (count > 1) {
char buffer[80];
sprintf(buffer, "AFS::BOS: can't specify more than one restart time at a time\n");
BSETCODE(-1, buffer);
goto done;
}
if (count == 0)
type = 1; /* by default set general restart time */
if (code = ktime_ParsePeriodic(time, &restartTime)) {
char buffer[240];
sprintf(buffer, "AFS::BOS: failed to parse '%s' as periodic restart time(%s)\n",
time, em(code));
BSETCODE(code, buffer);
goto done;
}
code = BOZO_SetRestartTime(self, type, &restartTime);
if (code) {
char buffer[240];
sprintf(buffer, "AFS::BOS: failed to set restart time at server (%s)\n", em(code));
BSETCODE(code, buffer);
goto done;
}
code = 0;
SETCODE(code);
done:
RETVAL = (code == 0);
}
OUTPUT:
RETVAL
void
bos_getrestart(self)
AFS::BOS self
PREINIT:
int32 code = 0;
struct ktime generalTime, newBinaryTime;
char messageBuffer[256];
PPCODE:
{
code = BOZO_GetRestartTime(self, 1, &generalTime);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to retrieve restart information (%s)\n", em(code));
BSETCODE(code, buffer);
XSRETURN_UNDEF;
}
code = BOZO_GetRestartTime(self, 2, &newBinaryTime);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to retrieve restart information (%s)\n", em(code));
BSETCODE(code, buffer);
XSRETURN_UNDEF;
}
code = ktime_DisplayString(&generalTime, messageBuffer);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to decode restart time (%s)\n", em(code));
BSETCODE(code, buffer);
strcpy(messageBuffer, "");
}
XPUSHs(sv_2mortal(newSVpv(messageBuffer, strlen(messageBuffer))));
code = ktime_DisplayString(&newBinaryTime, messageBuffer);
if (code) {
char buffer[256];
sprintf(buffer, "AFS::BOS: failed to decode restart time (%s)\n", em(code));
BSETCODE(code, buffer);
strcpy(messageBuffer, "");
}
XPUSHs(sv_2mortal(newSVpv(messageBuffer, strlen(messageBuffer))));
XSRETURN(2);
}
PPCODE:
{
SV *sv;
STRLEN len;
char *str;
struct ktc_token *t;
str = SvPV(s, len);
EXTEND(sp, 1);
if (len == sizeof(struct ktc_token)) {
t = (struct ktc_token *) safemalloc(sizeof(struct ktc_token));
memcpy((void *) t, (void *) str, sizeof(struct ktc_token));
sv = sv_newmortal();
sv_setref_pv(sv, "AFS::KTC_TOKEN", (void *) t);
PUSHs(sv);
}
else {
PUSHs(&PL_sv_undef);
}
}
void
afs_ktc_SetToken(server,token,client,flags=0)
AFS::KTC_PRINCIPAL server
AFS::KTC_TOKEN token
AFS::KTC_PRINCIPAL client
int32 flags
PPCODE:
{
int32 code;
code = ktc_SetToken(server, token, client, flags);
SETCODE(code);
ST(0) = sv_2mortal(newSViv(code == 0));
XSRETURN(1);
}
void
afs_ktc_ForgetAllTokens()
PPCODE:
{
int32 code;
code = ktc_ForgetAllTokens();
SETCODE(code);
ST(0) = sv_2mortal(newSViv(code == 0));
XSRETURN(1);
}
void
afs_error_message(code)
int32 code
PPCODE:
{
ST(0) = sv_newmortal();
sv_setpv(ST(0), (char *) error_message(code));
XSRETURN(1);
}
/* this function is generated automatically by constant_gen */
/* You didn't think I would type in this crap did you? */
/* thats what perl is for :-) */
#if defined(AFS_3_4)
void
constant(name, arg=0)
char * name
int arg
PPCODE:
{
ST(0) = sv_newmortal();
errno = EINVAL;
switch (name[0]) {
case 'A':
switch (name[1]) {
case 'F':
switch (name[2]) {
case 'S':
if (strEQ(name,"AFSCONF_FAILURE")) sv_setiv(ST(0),AFSCONF_FAILURE);
else if (strEQ(name,"AFSCONF_FULL")) sv_setiv(ST(0),AFSCONF_FULL);
else if (strEQ(name,"AFSCONF_NOCELL")) sv_setiv(ST(0),AFSCONF_NOCELL);
else if (strEQ(name,"AFSCONF_NODB")) sv_setiv(ST(0),AFSCONF_NODB);
else if (strEQ(name,"AFSCONF_NOTFOUND")) sv_setiv(ST(0),AFSCONF_NOTFOUND);
else if (strEQ(name,"AFSCONF_SYNTAX")) sv_setiv(ST(0),AFSCONF_SYNTAX);
else if (strEQ(name,"AFSCONF_UNKNOWN")) sv_setiv(ST(0),AFSCONF_UNKNOWN);
else {
ST(0) = ST(1) = &PL_sv_undef;
return;
}
break;
default:
ST(0) = ST(1) = &PL_sv_undef;
return;
}
break;
case 'N':
switch (name[2]) {
case 'O':
if (strEQ(name,"ANONYMOUSID")) sv_setiv(ST(0),ANONYMOUSID);
else {
ST(0) = ST(1) = &PL_sv_undef;
return;
}
break;
case 'Y':
if (strEQ(name,"ANYUSERID")) sv_setiv(ST(0),ANYUSERID);
else {
ST(0) = ST(1) = &PL_sv_undef;
return;
}
break;
default:
ST(0) = ST(1) = &PL_sv_undef;
return;
}
break;
case 'U':
switch (name[2]) {
( run in 3.042 seconds using v1.01-cache-2.11-cpan-df04353d9ac )