#include <afsconfig.h>
#include <afs/param.h>
-RCSID
- ("$Header$");
#include <stdio.h>
#include <sys/types.h>
#include <afs/acl.h>
#include "afs/audit.h"
#include <afs/dir.h>
+#include <afs/afsutil.h>
+#include <afs/vol_prototypes.h>
+#include <afs/errors.h>
#include "volser.h"
+#include "voltrans_inline.h"
#include "volint.h"
-#include "volser_prototypes.h"
+#include "volser_internal.h"
+#include "physio.h"
+#include "dumpstuff.h"
extern int DoLogging;
-extern struct volser_trans *FindTrans(), *NewTrans(), *TransList();
extern struct afsconf_dir *tdir;
-/* Needed by Irix. Leave, or include a header */
-extern char *volutil_PartitionName();
-
extern void LogError(afs_int32 errcode);
/* Forward declarations */
#endif
afs_int32 localTid = 1;
-afs_int32 VolPartitionInfo(), VolNukeVolume(), VolCreateVolume(),
-VolDeleteVolume(), VolClone();
-afs_int32 VolReClone(), VolTransCreate(), VolGetNthVolume(), VolGetFlags(),
-VolForward(), VolDump();
-afs_int32 VolRestore(), VolEndTrans(), VolSetForwarding(), VolGetStatus(),
-VolSetInfo(), VolGetName();
-afs_int32 VolListPartitions(), VolListOneVolume(),
-VolXListOneVolume(), VolXListVolumes();
-afs_int32 VolListVolumes(), XVolListPartitions(), VolMonitor(),
-VolSetIdsTypes(), VolSetDate(), VolSetFlags();
+
+static afs_int32 VolPartitionInfo(struct rx_call *, char *pname,
+ struct diskPartition64 *);
+static afs_int32 VolNukeVolume(struct rx_call *, afs_int32, afs_uint32);
+static afs_int32 VolCreateVolume(struct rx_call *, afs_int32, char *,
+ afs_int32, afs_uint32, afs_uint32 *,
+ afs_int32 *);
+static afs_int32 VolDeleteVolume(struct rx_call *, afs_int32);
+static afs_int32 VolClone(struct rx_call *, afs_int32, afs_uint32,
+ afs_int32, char *, afs_uint32 *);
+static afs_int32 VolReClone(struct rx_call *, afs_int32, afs_int32);
+static afs_int32 VolTransCreate(struct rx_call *, afs_uint32, afs_int32,
+ afs_int32, afs_int32 *);
+static afs_int32 VolGetNthVolume(struct rx_call *, afs_int32, afs_uint32 *,
+ afs_int32 *);
+static afs_int32 VolGetFlags(struct rx_call *, afs_int32, afs_int32 *);
+static afs_int32 VolSetFlags(struct rx_call *, afs_int32, afs_int32 );
+static afs_int32 VolForward(struct rx_call *, afs_int32, afs_int32,
+ struct destServer *destination, afs_int32,
+ struct restoreCookie *cookie);
+static afs_int32 VolDump(struct rx_call *, afs_int32, afs_int32, afs_int32);
+static afs_int32 VolRestore(struct rx_call *, afs_int32, afs_int32,
+ struct restoreCookie *);
+static afs_int32 VolEndTrans(struct rx_call *, afs_int32, afs_int32 *);
+static afs_int32 VolSetForwarding(struct rx_call *, afs_int32, afs_int32);
+static afs_int32 VolGetStatus(struct rx_call *, afs_int32,
+ struct volser_status *);
+static afs_int32 VolSetInfo(struct rx_call *, afs_int32, struct volintInfo *);
+static afs_int32 VolGetName(struct rx_call *, afs_int32, char **);
+static afs_int32 VolListPartitions(struct rx_call *, struct pIDs *);
+static afs_int32 XVolListPartitions(struct rx_call *, struct partEntries *);
+static afs_int32 VolListOneVolume(struct rx_call *, afs_int32, afs_uint32,
+ volEntries *);
+static afs_int32 VolXListOneVolume(struct rx_call *, afs_int32, afs_uint32,
+ volXEntries *);
+static afs_int32 VolListVolumes(struct rx_call *, afs_int32, afs_int32,
+ volEntries *);
+static afs_int32 VolXListVolumes(struct rx_call *, afs_int32, afs_int32,
+ volXEntries *);
+static afs_int32 VolMonitor(struct rx_call *, transDebugEntries *);
+static afs_int32 VolSetIdsTypes(struct rx_call *, afs_int32, char [],
+ afs_int32, afs_uint32, afs_uint32,
+ afs_uint32);
+static afs_int32 VolSetDate(struct rx_call *, afs_int32, afs_int32);
/* this call unlocks all of the partition locks we've set */
int
-VPFullUnlock()
+VPFullUnlock_r(void)
{
register struct DiskPartition64 *tp;
for (tp = DiskPartitionList; tp; tp = tp->next) {
return 0;
}
+int
+VPFullUnlock(void)
+{
+ int code;
+ VOL_LOCK;
+ code = VPFullUnlock_r();
+ VOL_UNLOCK;
+ return code;
+}
+
/* get partition id from a name */
afs_int32
PartitionID(char *aname)
return 0;
}
+static struct Volume *
+VAttachVolumeByName_retry(Error *ec, char *partition, char *name, int mode)
+{
+ struct Volume *vp;
+
+ *ec = 0;
+ vp = VAttachVolumeByName(ec, partition, name, mode);
+
+#ifdef AFS_DEMAND_ATTACH_FS
+ {
+ int i;
+ /*
+ * The fileserver will take care of keeping track of how many
+ * demand-salvages have been performed, and will force the volume to
+ * ERROR if we've done too many. The limit on This loop is just a
+ * failsafe to prevent trying to salvage forever. We want to attempt
+ * attachment at least SALVAGE_COUNT_MAX times, since we want to
+ * avoid prematurely exiting this loop, if we can.
+ */
+ for (i = 0; i < SALVAGE_COUNT_MAX*2 && *ec == VSALVAGING; i++) {
+ sleep(SALVAGE_PRIO_UPDATE_INTERVAL);
+ vp = VAttachVolumeByName(ec, partition, name, mode);
+ }
+
+ if (*ec == VSALVAGING) {
+ *ec = VSALVAGE;
+ }
+ }
+#endif /* AFS_DEMAND_ATTACH_FS */
+
+ return vp;
+}
+
+static struct Volume *
+VAttachVolume_retry(Error *ec, afs_uint32 avolid, int amode)
+{
+ struct Volume *vp;
+
+ *ec = 0;
+ vp = VAttachVolume(ec, avolid, amode);
+
+#ifdef AFS_DEMAND_ATTACH_FS
+ {
+ int i;
+ /* see comment above in VAttachVolumeByName_retry */
+ for (i = 0; i < SALVAGE_COUNT_MAX*2 && *ec == VSALVAGING; i++) {
+ sleep(SALVAGE_PRIO_UPDATE_INTERVAL);
+ vp = VAttachVolume(ec, avolid, amode);
+ }
+
+ if (*ec == VSALVAGING) {
+ *ec = VSALVAGE;
+ }
+ }
+#endif /* AFS_DEMAND_ATTACH_FS */
+
+ return vp;
+}
+
/* the only attach function that takes a partition is "...ByName", so we use it */
-struct Volume *
+static struct Volume *
XAttachVolume(afs_int32 *error, afs_uint32 avolid, afs_int32 apartid, int amode)
{
char pbuf[30], vbuf[20];
- register struct Volume *tv;
if (ConvertPartition(apartid, pbuf, sizeof(pbuf))) {
*error = EINVAL;
*error = EINVAL;
return NULL;
}
- tv = VAttachVolumeByName((Error *)error, pbuf, vbuf, amode);
- return tv;
+
+ return VAttachVolumeByName_retry((Error *)error, pbuf, vbuf, amode);
}
/* Adapted from the file server; create a root directory for this volume */
{
DirHandle dir;
struct acl_accessList *ACL;
- ViceFid did;
+ AFSFid did;
Inode inodeNumber, nearInode;
struct VnodeDiskObject *vnode;
struct VnodeClassInfo *vcp = &VnodeClassInfo[vLarge];
IHandle_t *h;
FdHandle_t *fdP;
- int code;
afs_fsize_t length;
+ ssize_t nBytes;
+ afs_foff_t off;
vnode = (struct VnodeDiskObject *)malloc(SIZEOF_LARGEDISKVNODE);
if (!vnode)
vp->vnodeIndex[vLarge].handle->ih_ino);
fdP = IH_OPEN(h);
assert(fdP != NULL);
- code = FDH_SEEK(fdP, vnodeIndexOffset(vcp, 1), SEEK_SET);
- assert(code >= 0);
- code = FDH_WRITE(fdP, vnode, SIZEOF_LARGEDISKVNODE);
- assert(code == SIZEOF_LARGEDISKVNODE);
+ off = FDH_SEEK(fdP, vnodeIndexOffset(vcp, 1), SEEK_SET);
+ assert(off >= 0);
+ nBytes = FDH_WRITE(fdP, vnode, SIZEOF_LARGEDISKVNODE);
+ assert(nBytes == SIZEOF_LARGEDISKVNODE);
FDH_REALLYCLOSE(fdP);
IH_RELEASE(h);
VNDISK_GET_LEN(length, vnode);
return code;
}
-afs_int32
+static afs_int32
VolNukeVolume(struct rx_call *acid, afs_int32 apartID, afs_uint32 avolID)
{
char partName[50];
afs_int32 error;
+ Error verror;
register afs_int32 code;
struct Volume *tvp;
char caller[MAXKTCNAMELEN];
tvp = XAttachVolume(&error, avolID, apartID, V_VOLUPD);
code = nuke(partName, avolID);
if (tvp)
- VDetachVolume(&error, tvp);
+ VDetachVolume(&verror, tvp);
return code;
}
return code;
}
-afs_int32
+static afs_int32
VolCreateVolume(struct rx_call *acid, afs_int32 apart, char *aname,
afs_int32 atype, afs_uint32 aparent, afs_uint32 *avolid,
afs_int32 *atrans)
{
- afs_int32 error;
+ Error error;
register Volume *vp;
- afs_int32 junk; /* discardable error code */
+ Error junk; /* discardable error code */
afs_uint32 volumeID;
afs_int32 doCreateRoot = 1;
register struct volser_trans *tt;
VDetachVolume(&junk, vp); /* rather return the real error code */
return error;
}
+ VTRANS_OBJ_LOCK(tt);
tt->volume = vp;
*atrans = tt->tid;
- strcpy(tt->lastProcName, "CreateVolume");
- tt->rxCallPtr = acid;
+ TSetRxCall_r(tt, acid, "CreateVolume");
+ VTRANS_OBJ_UNLOCK(tt);
Log("1 Volser: CreateVolume: volume %u (%s) created\n", volumeID, aname);
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
return 0;
return code;
}
-afs_int32
+static afs_int32
VolDeleteVolume(struct rx_call *acid, afs_int32 atrans)
{
register struct volser_trans *tt;
- afs_int32 error;
+ Error error;
char caller[MAXKTCNAMELEN];
if (!afsconf_SuperUser(tdir, acid, caller))
}
if (DoLogging)
Log("%s is executing Delete Volume %u\n", caller, tt->volid);
- strcpy(tt->lastProcName, "DeleteVolume");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "DeleteVolume");
VPurgeVolume(&error, tt->volume); /* don't check error code, it is not set! */
V_destroyMe(tt->volume) = DESTROY_ME; /* so endtrans does the right fssync opcode */
+ VTRANS_OBJ_LOCK(tt);
tt->vflags |= VTDeleted; /* so we know not to do anything else to it */
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall_r(tt);
+ VTRANS_OBJ_UNLOCK(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
/* make a clone of the volume associated with atrans, possibly giving it a new
* number (allocate a new number if *newNumber==0, otherwise use *newNumber
- * for the clone's id). The new clone is given the name newName. Finally, due to
- * efficiency considerations, if purgeId is non-zero, we purge that volume when doing
- * the clone operation. This may be useful when making new backup volumes, for instance
- * since the net result of a clone and a purge generally leaves many inode ref counts
- * the same, while doing them separately would result in far more iincs and idecs being
- * peformed (and they are slow operations).
+ * for the clone's id). The new clone is given the name newName. Finally,
+ * due to efficiency considerations, if purgeId is non-zero, we purge that
+ * volume when doing the clone operation. This may be useful when making
+ * new backup volumes, for instance since the net result of a clone and a
+ * purge generally leaves many inode ref counts the same, while doing them
+ * separately would result in far more iincs and idecs being peformed
+ * (and they are slow operations).
*/
/* for efficiency reasons, sometimes faster to piggyback a purge here */
afs_int32
return code;
}
-afs_int32
+static afs_int32
VolClone(struct rx_call *acid, afs_int32 atrans, afs_uint32 purgeId,
afs_int32 newType, char *newName, afs_uint32 *newNumber)
{
ttc = NewTrans(newId, tt->partition);
if (!ttc) { /* someone is messing with the clone already */
TRELE(tt);
- return VBUSY;
+ return VOLSERVOLBUSY;
}
- strcpy(tt->lastProcName, "Clone");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "Clone");
if (purgeId) {
- purgevp = VAttachVolume(&error, purgeId, V_VOLUPD);
+ purgevp = VAttachVolume_retry(&error, purgeId, V_VOLUPD);
if (error) {
Log("1 Volser: Clone: Could not attach 'purge' volume %u; clone aborted\n", purgeId);
goto fail;
LogError(error);
goto fail;
}
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt)) {
tt = (struct volser_trans *)0;
error = VOLSERTRELE_ERROR;
if (newvp)
VDetachVolume(&code, newvp);
if (tt) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
}
if (ttc)
return code;
}
-afs_int32
+static afs_int32
VolReClone(struct rx_call *acid, afs_int32 atrans, afs_int32 cloneId)
{
register struct Volume *originalvp, *clonevp;
ttc = NewTrans(cloneId, tt->partition);
if (!ttc) { /* someone is messing with the clone already */
TRELE(tt);
- return VBUSY;
+ return VOLSERVOLBUSY;
}
- strcpy(tt->lastProcName, "ReClone");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "ReClone");
originalvp = tt->volume;
if ((V_type(originalvp) == backupVolume)
goto fail;
}
- clonevp = VAttachVolume(&error, cloneId, V_VOLUPD);
+ clonevp = VAttachVolume_retry(&error, cloneId, V_VOLUPD);
if (error) {
Log("1 Volser: can't attach clone %d\n", cloneId);
goto fail;
LogError(error);
goto fail;
}
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt)) {
tt = (struct volser_trans *)0;
error = VOLSERTRELE_ERROR;
if (clonevp)
VDetachVolume(&code, clonevp);
if (tt) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
}
if (ttc)
return code;
}
-afs_int32
+static afs_int32
VolTransCreate(struct rx_call *acid, afs_uint32 volume, afs_int32 partition,
afs_int32 iflags, afs_int32 *ttid)
{
register struct volser_trans *tt;
register Volume *tv;
- afs_int32 error, code;
+ afs_int32 error;
+ Error code;
afs_int32 mode;
char caller[MAXKTCNAMELEN];
DeleteTrans(tt, 1);
return error;
}
+ VTRANS_OBJ_LOCK(tt);
tt->volume = tv;
*ttid = tt->tid;
tt->iflags = iflags;
tt->vflags = 0;
- strcpy(tt->lastProcName, "TransCreate");
+ TSetRxCall_r(tt, NULL, "TransCreate");
+ VTRANS_OBJ_UNLOCK(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
return code;
}
-afs_int32
-VolGetNthVolume(struct rx_call *acid, afs_int32 aindex, afs_int32 *avolume,
+static afs_int32
+VolGetNthVolume(struct rx_call *acid, afs_int32 aindex, afs_uint32 *avolume,
afs_int32 *apart)
{
Log("1 Volser: GetNthVolume: Not yet implemented\n");
return code;
}
-afs_int32
+static afs_int32
VolGetFlags(struct rx_call *acid, afs_int32 atid, afs_int32 *aflags)
{
register struct volser_trans *tt;
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "GetFlags");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "GetFlags");
*aflags = tt->vflags;
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
return code;
}
-afs_int32
+static afs_int32
VolSetFlags(struct rx_call *acid, afs_int32 atid, afs_int32 aflags)
{
register struct volser_trans *tt;
register struct Volume *vp;
- afs_int32 error;
+ Error error;
char caller[MAXKTCNAMELEN];
if (!afsconf_SuperUser(tdir, acid, caller))
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "SetFlags");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "SetFlags");
vp = tt->volume; /* pull volume out of transaction */
/* check if we're allowed to make any updates */
V_inService(vp) = 1;
}
VUpdateVolume(&error, vp);
+ VTRANS_OBJ_LOCK(tt);
tt->vflags = aflags;
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall_r(tt);
+ VTRANS_OBJ_UNLOCK(tt);
if (TRELE(tt) && !error)
return VOLSERTRELE_ERROR;
return code;
}
-afs_int32
+static afs_int32
VolForward(struct rx_call *acid, afs_int32 fromTrans, afs_int32 fromDate,
struct destServer *destination, afs_int32 destTrans,
struct restoreCookie *cookie)
return ENOENT;
}
vp = tt->volume;
- strcpy(tt->lastProcName, "Forward");
+ TSetRxCall(tt, NULL, "Forward");
/* get auth info for the this connection (uses afs from ticket file) */
code = afsconf_ClientAuth(tdir, &securityObject, &securityIndex);
htons(destination->destPort), VOLSERVICE_ID,
securityObject, securityIndex);
if (!tcon) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
return ENOTCONN;
}
tcall = rx_NewCall(tcon);
- tt->rxCallPtr = tcall;
+ TSetRxCall(tt, tcall, "Forward");
/* start restore going. fromdate == 0 --> doing an incremental dump/restore */
code = StartAFSVolRestore(tcall, destTrans, (fromDate ? 1 : 0), cookie);
if (code) {
if (code)
goto fail;
EndAFSVolRestore(tcall); /* probably doesn't do much */
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
code = rx_EndCall(tcall, 0);
rx_DestroyConnection(tcon); /* done with the connection */
tcon = NULL;
rx_DestroyConnection(tcon);
}
if (tt) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
}
return code;
return ENOENT;
}
vp = tt->volume;
- strcpy(tt->lastProcName, "ForwardMulti");
+ TSetRxCall(tt, NULL, "ForwardMulti");
/* (fromDate == 0) ==> full dump */
is_incremental = (fromDate ? 1 : 0);
free(tcalls);
if (tt) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt) && !code) /* return the first code if it's set */
return VOLSERTRELE_ERROR;
}
}
afs_int32
-SAFSVolDumpV2(struct rx_call *acid, afs_int32 fromTrans, afs_int32 fromDate, afs_int32 flags)
+SAFSVolDumpV2(struct rx_call *acid, afs_int32 fromTrans, afs_int32 fromDate,
+ afs_int32 flags)
{
afs_int32 code;
return code;
}
-afs_int32
-VolDump(struct rx_call *acid, afs_int32 fromTrans, afs_int32 fromDate, afs_int32 flags)
+static afs_int32
+VolDump(struct rx_call *acid, afs_int32 fromTrans, afs_int32 fromDate,
+ afs_int32 flags)
{
int code = 0;
register struct volser_trans *tt;
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "Dump");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "Dump");
code = DumpVolume(acid, tt->volume, fromDate, (flags & VOLDUMPV2_OMITDIRS)
? 0 : 1); /* squirt out the volume's data, too */
if (code) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
return code;
}
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
* Ha! No more helper process!
*/
afs_int32
-SAFSVolRestore(struct rx_call *acid, afs_int32 atrans, afs_int32 aflags,
+SAFSVolRestore(struct rx_call *acid, afs_int32 atrans, afs_int32 aflags,
struct restoreCookie *cookie)
{
afs_int32 code;
return code;
}
-afs_int32
-VolRestore(struct rx_call *acid, afs_int32 atrans, afs_int32 aflags,
- struct restoreCookie *cookie)
+static afs_int32
+VolRestore(struct rx_call *acid, afs_int32 atrans, afs_int32 aflags,
+ struct restoreCookie *cookie)
{
register struct volser_trans *tt;
register afs_int32 code, tcode;
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "Restore");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "Restore");
DFlushVolume(V_parentId(tt->volume)); /* Ensure dir buffers get dropped */
code = RestoreVolume(acid, tt->volume, (aflags & 1), cookie); /* last is incrementalp */
FSYNC_VolOp(tt->volid, NULL, FSYNC_VOL_BREAKCBKS, 0l, NULL);
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
tcode = TRELE(tt);
return (code ? code : tcode);
return code;
}
-afs_int32
+static afs_int32
VolEndTrans(struct rx_call *acid, afs_int32 destTrans, afs_int32 *rcode)
{
register struct volser_trans *tt;
return code;
}
-afs_int32
+static afs_int32
VolSetForwarding(struct rx_call *acid, afs_int32 atid, afs_int32 anewsite)
{
register struct volser_trans *tt;
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "SetForwarding");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "SetForwarding");
if (volutil_PartitionName2_r(tt->partition, partName, sizeof(partName)) != 0) {
partName[0] = '\0';
}
FSYNC_VolOp(tt->volid, partName, FSYNC_VOL_MOVE, anewsite, NULL);
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
}
afs_int32
-SAFSVolGetStatus(struct rx_call *acid, afs_int32 atrans,
+SAFSVolGetStatus(struct rx_call *acid, afs_int32 atrans,
register struct volser_status *astatus)
{
afs_int32 code;
return code;
}
-afs_int32
-VolGetStatus(struct rx_call *acid, afs_int32 atrans,
- register struct volser_status *astatus)
+static afs_int32
+VolGetStatus(struct rx_call *acid, afs_int32 atrans,
+ register struct volser_status *astatus)
{
register struct Volume *tv;
register struct VolumeDiskData *td;
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "GetStatus");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "GetStatus");
tv = tt->volume;
if (!tv) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
return ENOENT;
}
astatus->expirationDate = td->expirationDate;
astatus->backupDate = td->backupDate;
astatus->copyDate = td->copyDate;
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
}
afs_int32
-SAFSVolSetInfo(struct rx_call *acid, afs_int32 atrans,
+SAFSVolSetInfo(struct rx_call *acid, afs_int32 atrans,
register struct volintInfo *astatus)
{
afs_int32 code;
return code;
}
-afs_int32
-VolSetInfo(struct rx_call *acid, afs_int32 atrans,
+static afs_int32
+VolSetInfo(struct rx_call *acid, afs_int32 atrans,
register struct volintInfo *astatus)
{
register struct Volume *tv;
register struct VolumeDiskData *td;
struct volser_trans *tt;
char caller[MAXKTCNAMELEN];
- afs_int32 error;
+ Error error;
if (!afsconf_SuperUser(tdir, acid, caller))
return VOLSERBAD_ACCESS; /*not a super user */
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "SetStatus");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "SetStatus");
tv = tt->volume;
if (!tv) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
return ENOENT;
}
if (astatus->spare2 != -1)
td->volUpdateCounter = (unsigned int)astatus->spare2;
VUpdateVolume(&error, tv);
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
return 0;
return code;
}
-afs_int32
+static afs_int32
VolGetName(struct rx_call *acid, afs_int32 atrans, char **aname)
{
register struct Volume *tv;
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "GetName");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "GetName");
tv = tt->volume;
if (!tv) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
return ENOENT;
}
td = &tv->header->diskstuff;
len = strlen(td->name) + 1; /* don't forget the null */
if (len >= SIZE) {
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
TRELE(tt);
return E2BIG;
}
*aname = (char *)realloc(*aname, len);
strcpy(*aname, td->name);
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
/*this is a handshake to indicate that the next call will be SAFSVolRestore
* - a noop now !*/
afs_int32
-SAFSVolSignalRestore(struct rx_call *acid, char volname[], int volType,
+SAFSVolSignalRestore(struct rx_call *acid, char volname[], int volType,
afs_uint32 parentId, afs_uint32 cloneId)
{
return 0;
return code;
}
-afs_int32
+static afs_int32
VolListPartitions(struct rx_call *acid, struct pIDs *partIds)
{
char namehead[9];
- char i;
+ int i;
strcpy(namehead, "/vicep"); /*7 including null terminator */
return code;
}
-afs_int32
+static afs_int32
XVolListPartitions(struct rx_call *acid, struct partEntries *pEntries)
{
char namehead[9];
struct partList partList;
struct DiskPartition64 *dp;
- int i, j = 0, k;
+ int i, j = 0;
strcpy(namehead, "/vicep"); /*7 including null terminator */
namehead[6] = i + 'a';
namehead[7] = '\0';
} else {
+ int k;
+
k = i - 26;
namehead[6] = 'a' + (k / 26);
namehead[7] = 'a' + (k % 26);
* Copy out the stat fields in a single operation.
*/
if ((now - hdr->dayUseDate) > OneDay) {
- memset((char *)&(handle->volinfo_ptr.ext->stat_reads[0]),
+ memset(&(handle->volinfo_ptr.ext->stat_reads[0]),
0, numStatBytes);
} else {
memcpy((char *)&(handle->volinfo_ptr.ext->stat_reads[0]),
return 0;
}
+#ifdef AFS_DEMAND_ATTACH_FS
+
/**
* get struct Volume out of the fileserver.
*
return code;
}
+#endif
+
/**
* mode of volume list operation.
*/
vol_info_list_mode_t mode)
{
int code = -1;
- afs_int32 error;
+ Error error;
struct volser_trans *ttc = NULL;
struct Volume *fill_tv, *tv = NULL;
#ifdef AFS_DEMAND_ATTACH_FS
ttc = NewTrans(volumeId, partId);
if (!ttc) {
code = -3;
- VOLINT_INFO_STORE(handle, status, VBUSY);
+ VOLINT_INFO_STORE(handle, status, VOLSERVOLBUSY);
VOLINT_INFO_STORE(handle, volid, volumeId);
goto drop;
}
/* Get volume from volserver */
- tv = VAttachVolumeByName(&error, pname, volname, V_PEEK);
+ tv = VAttachVolumeByName_retry(&error, pname, volname, V_PEEK);
if (error) {
Log("1 Volser: GetVolInfo: Could not attach volume %u (%s:%s) error=%d\n",
volumeId, pname, volname, error);
#ifdef AFS_DEMAND_ATTACH_FS
/* If using DAFS, get volume from fsserver */
- if (GetVolObject(volumeId, pname, &fs_tv) != SYNC_OK) {
+ if (GetVolObject(volumeId, pname, &fs_tv) != SYNC_OK || fs_tv == NULL) {
+
goto drop;
}
return code;
}
-afs_int32
+static afs_int32
VolListOneVolume(struct rx_call *acid, afs_int32 partid,
afs_uint32 volumeId, volEntries *volumeInfo)
{
volintInfo *pntr;
struct DiskPartition64 *partP;
char pname[9], volname[20];
- afs_int32 error = 0;
DIR *dirp;
afs_uint32 volid;
int found = 0;
return code;
}
-afs_int32
+static afs_int32
VolXListOneVolume(struct rx_call *a_rxCidP, afs_int32 a_partID,
afs_uint32 a_volID, volXEntries *a_volumeXInfoP)
{ /*SAFSVolXListOneVolume */
return code;
}
-afs_int32
+static afs_int32
VolListVolumes(struct rx_call *acid, afs_int32 partid, afs_int32 flags,
volEntries *volumeInfo)
{
struct DiskPartition64 *partP;
afs_int32 allocSize = 1000; /*to be changed to a larger figure */
char pname[9], volname[20];
- afs_int32 error = 0;
DIR *dirp;
afs_uint32 volid;
int code;
/*just volids are needed */
}
- drop:
pntr++;
volumeInfo->volEntries_len += 1;
if ((allocSize - volumeInfo->volEntries_len) < 5) {
return code;
}
-afs_int32
+static afs_int32
VolXListVolumes(struct rx_call *a_rxCidP, afs_int32 a_partID,
afs_int32 a_flags, volXEntries *a_volumeXInfoP)
{ /*SAFSVolXListVolumes */
struct DiskPartition64 *partP; /*Ptr to partition */
afs_int32 allocSize = 1000; /*To be changed to a larger figure */
char pname[9], volname[20]; /*Partition, volume names */
- afs_int32 error = 0; /*Return code */
DIR *dirp; /*Partition directory ptr */
afs_uint32 volid; /*Current volume ID */
int code;
xInfoP->volid = volid;
}
- drop:
/*
* Bump the pointer in the data area we're building, along with
* the count of the number of entries it contains.
return code;
}
-afs_int32
+static afs_int32
VolMonitor(struct rx_call *acid, transDebugEntries *transInfo)
{
transDebugInfo *pntr;
afs_int32 allocSize = 50;
- struct volser_trans *tt, *allTrans;
+ struct volser_trans *tt, *nt, *allTrans;
transInfo->transDebugEntries_val =
(transDebugInfo *) malloc(allocSize * sizeof(transDebugInfo));
return ENOMEM;
pntr = transInfo->transDebugEntries_val;
transInfo->transDebugEntries_len = 0;
+
+ VTRANS_LOCK;
allTrans = TransList();
if (allTrans == (struct volser_trans *)0)
- return 0; /*no active transactions */
- for (tt = allTrans; tt; tt = tt->next) { /*copy relevant info into pntr */
+ goto done; /*no active transactions */
+ for (tt = allTrans; tt; tt = nt) { /*copy relevant info into pntr */
+ nt = tt->next;
+ VTRANS_OBJ_LOCK(tt);
pntr->tid = tt->tid;
pntr->time = tt->time;
pntr->creationTime = tt->creationTime;
pntr->lastSendTime = tt->rxCallPtr->lastSendTime;
pntr->lastReceiveTime = tt->rxCallPtr->lastReceiveTime;
}
+ VTRANS_OBJ_UNLOCK(tt);
pntr++;
transInfo->transDebugEntries_len += 1;
if ((allocSize - transInfo->transDebugEntries_len) < 5) { /*alloc some more space */
}
}
+done:
+ VTRANS_UNLOCK;
return 0;
}
afs_int32
-SAFSVolSetIdsTypes(struct rx_call *acid, afs_int32 atid, char name[], afs_int32 type, afs_uint32 pId, afs_uint32 cloneId, afs_uint32 backupId)
+SAFSVolSetIdsTypes(struct rx_call *acid, afs_int32 atid, char name[],
+ afs_int32 type, afs_uint32 pId, afs_uint32 cloneId,
+ afs_uint32 backupId)
{
afs_int32 code;
return code;
}
-afs_int32
-VolSetIdsTypes(struct rx_call *acid, afs_int32 atid, char name[], afs_int32 type, afs_uint32 pId, afs_uint32 cloneId, afs_uint32 backupId)
+static afs_int32
+VolSetIdsTypes(struct rx_call *acid, afs_int32 atid, char name[],
+ afs_int32 type, afs_uint32 pId, afs_uint32 cloneId,
+ afs_uint32 backupId)
{
struct Volume *tv;
- afs_int32 error = 0;
+ Error error = 0;
register struct volser_trans *tt;
char caller[MAXKTCNAMELEN];
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "SetIdsTypes");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "SetIdsTypes");
tv = tt->volume;
V_type(tv) = type;
LogError(error);
goto fail;
}
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt) && !error)
return VOLSERTRELE_ERROR;
return error;
fail:
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt) && !error)
return VOLSERTRELE_ERROR;
return error;
return code;
}
-afs_int32
+static afs_int32
VolSetDate(struct rx_call *acid, afs_int32 atid, afs_int32 cdate)
{
struct Volume *tv;
- afs_int32 error = 0;
+ Error error = 0;
register struct volser_trans *tt;
char caller[MAXKTCNAMELEN];
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "SetDate");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "SetDate");
tv = tt->volume;
V_creationDate(tv) = cdate;
LogError(error);
goto fail;
}
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt) && !error)
return VOLSERTRELE_ERROR;
return error;
fail:
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt) && !error)
return VOLSERTRELE_ERROR;
return error;
#endif
ttc = NewTrans(volumeId, partId);
if (!ttc) {
- return VBUSY;
+ return VOLSERVOLBUSY;
}
#ifdef AFS_NAMEI_ENV
ret = namei_ConvertROtoRWvolume(pname, volumeId);
TRELE(tt);
return ENOENT;
}
- strcpy(tt->lastProcName, "GetSize");
- tt->rxCallPtr = acid;
+ TSetRxCall(tt, acid, "GetSize");
code = SizeDumpVolume(acid, tt->volume, fromDate, 1, size); /* measure volume's data */
- tt->rxCallPtr = (struct rx_call *)0;
+ TClearRxCall(tt);
if (TRELE(tt))
return VOLSERTRELE_ERROR;
}
afs_int32
-SAFSVolSplitVolume(struct rx_call *acall, afs_uint32 vid, afs_uint32 new,
+SAFSVolSplitVolume(struct rx_call *acall, afs_uint32 vid, afs_uint32 new,
afs_uint32 where, afs_int32 verbose)
{
- afs_int32 code, code2;
+#if defined(AFS_NAMEI_ENV) && !defined(AFS_NT40_ENV)
+ Error code, code2;
Volume *vol=0, *newvol=0;
struct volser_trans *tt = 0, *tt2 = 0;
char caller[MAXKTCNAMELEN];
VDetachVolume(&code2, newvol);
return VOLSERVOLBUSY;
}
+ VTRANS_OBJ_LOCK(tt);
tt->iflags = ITBusy;
tt->vflags = 0;
- strcpy(tt->lastProcName, "SplitVolume");
+ TSetRxCall_r(tt, NULL, "SplitVolume");
+ VTRANS_OBJ_UNLOCK(tt);
tt2 = NewTrans(new, V_device(newvol));
if (!tt2) {
VDetachVolume(&code2, newvol);
return VOLSERVOLBUSY;
}
+ VTRANS_OBJ_LOCK(tt2);
tt2->iflags = ITBusy;
tt2->vflags = 0;
- strcpy(tt2->lastProcName, "SplitVolume");
+ TSetRxCall_r(tt2, NULL, "SplitVolume");
+ VTRANS_OBJ_UNLOCK(tt2);
code = split_volume(acall, vol, newvol, where, verbose);
VDetachVolume(&code2, newvol);
DeleteTrans(tt2, 1);
return code;
+#else
+ return VOLSERBADOP;
+#endif
}
/* GetPartName - map partid (a decimal number) into pname (a string)