Loading...
Searching...
No Matches
XrdSsiFileSess.cc
Go to the documentation of this file.
/******************************************************************************/
/* */
/* X r d S s i F i l e S e s s . c c */
/* */
/* (c) 2016 by the Board of Trustees of the Leland Stanford, Jr., University */
/* Produced by Andrew Hanushevsky for Stanford University under contract */
/* DE-AC02-76-SFO0515 with the Department of Energy */
/* */
/* This file is part of the XRootD software suite. */
/* */
/* XRootD is free software: you can redistribute it and/or modify it under */
/* the terms of the GNU Lesser General Public License as published by the */
/* Free Software Foundation, either version 3 of the License, or (at your */
/* option) any later version. */
/* */
/* XRootD is distributed in the hope that it will be useful, but WITHOUT */
/* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or */
/* FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public */
/* License for more details. */
/* */
/* You should have received a copy of the GNU Lesser General Public License */
/* along with XRootD in a file called COPYING.LESSER (LGPL license) and file */
/* COPYING (GPL license). If not, see <http://www.gnu.org/licenses/>. */
/* */
/* The copyright holder's institutional names and contributor's names may not */
/* be used to endorse or promote products derived from this software without */
/* specific prior written permission of the institution or contributor. */
/******************************************************************************/
#include <fcntl.h>
#include <stddef.h>
#include <cstdio>
#include <cstring>
#include <arpa/inet.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/uio.h>
#include "XrdNet/XrdNetAddrInfo.hh"
#include "XrdOuc/XrdOucBuffer.hh"
#include "XrdOuc/XrdOucEnv.hh"
#include "XrdOuc/XrdOucERoute.hh"
#include "XrdOuc/XrdOucPList.hh"
#include "XrdSec/XrdSecEntity.hh"
#include "XrdSfs/XrdSfsAio.hh"
#include "XrdSsi/XrdSsiEntity.hh"
#include "XrdSsi/XrdSsiFileSess.hh"
#include "XrdSsi/XrdSsiProvider.hh"
#include "XrdSsi/XrdSsiRRInfo.hh"
#include "XrdSsi/XrdSsiService.hh"
#include "XrdSsi/XrdSsiSfs.hh"
#include "XrdSsi/XrdSsiStats.hh"
#include "XrdSsi/XrdSsiStream.hh"
#include "XrdSsi/XrdSsiTrace.hh"
#include "XrdSsi/XrdSsiUtils.hh"
#include "XrdSys/XrdSysE2T.hh"
#include "XrdSys/XrdSysError.hh"
/******************************************************************************/
/* G l o b a l s */
/******************************************************************************/
namespace XrdSsi
{
extern XrdOucBuffPool *BuffPool;
extern XrdSsiProvider *Provider;
extern XrdSsiService *Service;
extern XrdSsiStats Stats;
extern XrdSysError Log;
extern int respWT;
extern int minRSZ;
extern int maxRSZ;
}
using namespace XrdSsi;
/******************************************************************************/
/* L o c a l M a c r o s */
/******************************************************************************/
#define DUMPIT(x,y) XrdSsiUtils::b2x(x,y,hexBuff,sizeof(hexBuff),dotBuff)<<dotBuff
/******************************************************************************/
/* L o c a l C l a s s e s */
/******************************************************************************/
namespace
{
class nullCallBack : public XrdOucEICB
{
public:
void Done(int &Result, XrdOucErrInfo *eInfo, const char *Path=0) {}
int Same(unsigned long long arg1, unsigned long long arg2) {return 0;}
nullCallBack() {}
virtual ~nullCallBack() {}
};
nullCallBack nullCB;
};
/******************************************************************************/
/* S t a t i c M e m b e r s */
/******************************************************************************/
XrdSysMutex XrdSsiFileSess::arMutex;
XrdSsiFileSess *XrdSsiFileSess::freeList = 0;
int XrdSsiFileSess::freeNum = 0;
int XrdSsiFileSess::freeNew = 0;
int XrdSsiFileSess::freeMax = 100;
int XrdSsiFileSess::freeAbs = 200;
bool XrdSsiFileSess::authDNS = false;
/******************************************************************************/
/* A l l o c */
/******************************************************************************/
XrdSsiFileSess *XrdSsiFileSess::Alloc(XrdOucErrInfo &einfo, const char *user)
{
XrdSsiFileSess *fsP;
// Get a lock
//
arMutex.Lock();
// Get either a reuseable object or a new one
//
if ((fsP = freeList))
{freeNum--;
freeList = fsP->nextFree;
arMutex.UnLock();
fsP->Init(einfo, user, true);
} else {
freeNew++;
if (freeMax <= freeAbs && freeNew >= freeMax/2)
{freeMax += freeMax/2;
freeNew = 0;
}
arMutex.UnLock();
fsP = new XrdSsiFileSess(einfo, user);
}
// Return the object
//
return fsP;
}
/******************************************************************************/
/* A t t n I n f o */
/******************************************************************************/
bool XrdSsiFileSess::AttnInfo(XrdOucErrInfo &eInfo, const XrdSsiRespInfo *respP,
unsigned int reqID)
// Called with the request mutex locked!
{
EPNAME("AttnInfo");
struct AttnResp {struct iovec ioV[4]; XrdSsiRRInfoAttn aHdr;};
AttnResp *attnResp;
char *mBuff;
int n, ioN = 2;
bool doFin;
// If there is no data we can send back to the client in the attn response,
// then simply reply with a short message to make the client come back.
//
if (!respP->mdlen)
{if (respP->rType != XrdSsiRespInfo::isData
|| respP->blen > XrdSsiResponder::MaxDirectXfr)
{eInfo.setErrInfo(0, "");
return false;
}
}
// We will be constructing the response in the message buffer. This is
// gauranteed to be big enough for our purposes so no need to check the size.
//
mBuff = eInfo.getMsgBuff(n);
// Initialize the response
//
attnResp = (AttnResp *)mBuff;
memset(attnResp, 0, sizeof(AttnResp));
attnResp->aHdr.pfxLen = htons(sizeof(XrdSsiRRInfoAttn));
// Fill out iovec to point to our header
//
//?attnResp->ioV[0].iov_len = sizeof(XrdSsiRRInfoAttn) + respP->mdlen;
attnResp->ioV[1].iov_base = mBuff+offsetof(struct AttnResp, aHdr);
attnResp->ioV[1].iov_len = sizeof(XrdSsiRRInfoAttn);
// Fill out the iovec for the metadata if we have some
//
if (respP->mdlen)
{attnResp->ioV[2].iov_base = (void *)respP->mdata;
attnResp->ioV[2].iov_len = respP->mdlen; ioN = 3;
attnResp->aHdr.mdLen = htonl(respP->mdlen);
Stats.Bump(Stats.RspMDBytes, respP->mdlen);
if (QTRACE(Debug))
{char hexBuff[16],dotBuff[4];
DEBUG(reqID <<':' <<gigID <<' ' <<respP->mdlen <<" byte metadata (0x"
<<DUMPIT(respP->mdata,respP->mdlen) <<") sent.");
}
}
// Check if we have actual data here as well and can send it along
//
if (respP->rType == XrdSsiRespInfo::isData
&& respP->blen+respP->mdlen <= XrdSsiResponder::MaxDirectXfr)
{if (respP->blen)
{attnResp->ioV[ioN].iov_base = (void *)respP->buff;
attnResp->ioV[ioN].iov_len = respP->blen; ioN++;
}
attnResp->aHdr.tag = XrdSsiRRInfoAttn::fullResp; doFin = true;
}
else {attnResp->aHdr.tag = XrdSsiRRInfoAttn::pendResp; doFin = false;}
// If we sent the full response we must remove the request from the request
// table as it will get finished off when the response is actually sent.
//
if (doFin)
{XrdSsiRRTableItem<XrdSsiFileReq> rqstP;
if (!(rqstP = rTab.LookUp(reqID)))
{eInfo.setErrInfo(0, "");
return false;
}
attnFinCallBack.setReq(std::move(rqstP));
eInfo.setErrCB(&attnFinCallBack);
rTab.Del(reqID);
}
// Setup to have metadata actually sent to the requestor
//
eInfo.setErrCode(ioN);
return doFin;
}
/******************************************************************************/
/* c l o s e */
/******************************************************************************/
int XrdSsiFileSess::close(bool viaDel)
/*
Function: Close the file object.
Input: None
Output: Always returns SFS_OK
*/
{
const char *epname = "close";
// Do some debugging
//
DEBUG((gigID ? gigID : "???") <<" del=" <<viaDel);
// Collect statistics if this is a delete which implies a lost connection
//
if (viaDel)
{int rCnt = rTab.Num();
if (rCnt) Stats.Bump(Stats.ReqFinForce, rCnt);
}
// Run through all outstanding requests and comlete them
//
rTab.Reset();
// Free any in-progress buffers
//
if (inProg)
{if (oucBuff) {oucBuff->Recycle(); oucBuff = 0;}
inProg = false;
}
// Clean up storage
//
isOpen = false;
return SFS_OK;
}
/******************************************************************************/
/* f c t l */
/******************************************************************************/
int XrdSsiFileSess::fctl(const int cmd,
int alen,
const char *args,
const XrdSecEntity *client)
{
static const char *epname = "fctl";
XrdSsiRRInfo *rInfo;
XrdSsiRRTableItem<XrdSsiFileReq> rqstP;
unsigned int reqID;
// If this isn't the special query, then return an error
//
if (cmd != SFS_FCTL_SPEC1)
return XrdSsiUtils::Emsg(epname, ENOTSUP, "fctl", gigID, *eInfo);
// Caller wishes to find out if a request is ready and wait if it is not
//
if (!args || alen < (int)sizeof(XrdSsiRRInfo))
return XrdSsiUtils::Emsg(epname, EINVAL, "fctl", gigID, *eInfo);
// Grab the request identifier
//
rInfo = (XrdSsiRRInfo *)args;
reqID = rInfo->Id();
// Do some debugging
//
DEBUG(reqID <<':' <<gigID <<" query resp status");
// Find the request
//
if (!(rqstP = rTab.LookUp(reqID)))
return XrdSsiUtils::Emsg(epname, ESRCH, "fctl", gigID, *eInfo);
// Check if a response is waiting for the caller
//
if (rqstP->WantResponse(*eInfo))
{DEBUG(reqID <<':' <<gigID <<" resp ready");
Stats.Bump(Stats.RspReady);
return SFS_DATAVEC;
}
// Put this client into callback state
//
DEBUG(reqID <<':' <<gigID <<" resp not ready");
fctlCallBack.setReq(std::move(rqstP));
eInfo->setErrCB(&fctlCallBack);
eInfo->setErrInfo(respWT, "");
Stats.Bump(Stats.RspUnRdy);
return SFS_STARTED;
}
/******************************************************************************/
/* Private: I n i t */
/******************************************************************************/
void XrdSsiFileSess::Init(XrdOucErrInfo &einfo, const char *user, bool forReuse)
{
tident = (user ? strdup(user) : strdup(""));
eInfo = &einfo;
gigID = 0;
fsUser = 0;
xioP = 0;
oucBuff = 0;
reqSize = 0;
reqLeft = 0;
isOpen = false;
inProg = false;
if (forReuse)
{eofVec.Reset();
rTab.Clear();
}
}
/******************************************************************************/
/* Private: N e w R e q u e s t */
/******************************************************************************/
bool XrdSsiFileSess::NewRequest(unsigned int reqid,
XrdOucBuffer *oP,
XrdSfsXioHandle bR,
int rSz)
{
XrdSsiFileReq *reqP;
// Allocate a new request object
//
if (!(reqP=XrdSsiFileReq::Alloc(eInfo,&fileResource,this,gigID,tident,reqid)))
return false;
// Add it to the table
//
XrdSsiRRTableItem<XrdSsiFileReq> rqstP = rTab.Add(reqP, reqid);
if (!rqstP)
{delete reqP;
return false;
}
// Activate the request
//
inProg = false;
rqstP->Activate(oP, bR, rSz);
return true;
}
/******************************************************************************/
/* o p e n */
/******************************************************************************/
int XrdSsiFileSess::open(const char *path, // In
XrdOucEnv &theEnv, // In
XrdSfsFileOpenMode open_mode) // In
/*
Function: Open the file `path' in the mode indicated by `open_mode'.
Input: path - The fully qualified name of the resource.
theEnv - Environmental information.
open_mode - It must contain only SFS_O_RDWR.
Output: Returns SFS_OK upon success, otherwise SFS_ERROR is returned.
*/
{
static const char *epname = "open";
XrdSsiErrInfo errInfo;
const char *eText;
int eNum;
// Verify that this object is not already associated with an open file
//
if (isOpen)
return XrdSsiUtils::Emsg(epname, EADDRINUSE, "open session", path, *eInfo);
// Make sure the open flag is correct (we now open this R/O so don't check)
//
// if (open_mode != SFS_O_RDWR)
// return XrdSsiUtils::Emsg(epname, EPROTOTYPE, "open session", path, *eInfo);
// Setup the file resource object
//
fileResource.Init(path, theEnv, authDNS);
// Notify the provider that we will be executing a request
//
if (Service->Prepare(errInfo, fileResource))
{const char *usr = fileResource.rUser.c_str();
if (!(*usr)) gigID = strdup(path);
else {char gBuff[2048];
snprintf(gBuff, sizeof(gBuff), "%s:%s", usr, path);
gigID = strdup(gBuff);
}
DEBUG(gigID <<" prepared.");
isOpen = true;
return SFS_OK;
}
// Get error information
//
eText = errInfo.Get(eNum).c_str();
if (!eNum)
{eNum = ENOMSG; eText = "Provider returned invalid prepare response.";}
// Decode the error
//
switch(eNum)
{case EAGAIN:
if (!eText || !(*eText)) break;
eNum = errInfo.GetArg();
DEBUG(path <<" --> " <<eText <<':' <<eNum);
eInfo->setErrInfo(eNum, eText);
Stats.Bump(Stats.ReqRedir);
return SFS_REDIRECT;
break;
case EBUSY:
eNum = errInfo.GetArg();
if (!eText || !(*eText)) eText = "Provider is busy.";
DEBUG(path <<" dly " <<eNum <<' ' <<eText);
if (eNum <= 0) eNum = 1;
eInfo->setErrInfo(eNum, eText);
Stats.Bump(Stats.ReqStalls);
return eNum;
break;
default:
if (!eText || !(*eText)) eText = XrdSysE2T(eNum);
DEBUG(path <<" err " <<eNum <<' ' <<eText);
eInfo->setErrInfo(eNum, eText);
Stats.Bump(Stats.ReqPrepErrs);
return SFS_ERROR;
break;
};
// Something is quite wrong here
//
Log.Emsg(epname, "Provider redirect returned no target host name!");
eInfo->setErrInfo(ENOMSG, "Server logic error");
Stats.Bump(Stats.ReqPrepErrs);
return SFS_ERROR;
}
/******************************************************************************/
/* r e a d */
/******************************************************************************/
XrdSfsXferSize XrdSsiFileSess::read(XrdSfsFileOffset offset, // In
char *buff, // Out
XrdSfsXferSize blen) // In
/*
Function: Read `blen' bytes at `offset' into 'buff' and return the actual
number of bytes read.
Input: offset - Contains request information.
buff - Address of the buffer in which to place the data.
blen - The size of the buffer. This is the maximum number
of bytes that will be returned.
Output: Returns the number of bytes read upon success and SFS_ERROR o/w.
*/
{
static const char *epname = "read";
XrdSsiRRInfo rInfo(offset);
XrdSsiRRTableItem<XrdSsiFileReq> rqstP;
XrdSfsXferSize retval;
unsigned int reqID = rInfo.Id();
bool noMore = false;
// Find the request object. If not there we may have encountered an eof
//
if (!(rqstP = rTab.LookUp(reqID)))
{if (eofVec.IsSet(reqID))
{eofVec.UnSet(reqID);
return 0;
}
return XrdSsiUtils::Emsg(epname, ESRCH, "read", gigID, *eInfo);
}
// Simply effect the read via the request object
//
retval = rqstP->Read(noMore, buff, blen);
// See if we just completed this request
//
if (noMore)
{rTab.DelFinalize(std::move(rqstP));
eofVec.Set(reqID);
}
// All done
//
return retval;
}
/******************************************************************************/
/* R e c y c l e */
/******************************************************************************/
void XrdSsiFileSess::Recycle()
{
// Do an immediate reset on ourselves to avoid getting too many locks
//
Reset();
// Get a lock
//
arMutex.Lock();
// Check if we should place this on the free list or simply delete it
//
if (freeNum < freeMax)
{nextFree = freeList;
freeList = this;
freeNum++;
arMutex.UnLock();
} else {
arMutex.UnLock();
delete this;
}
}
/******************************************************************************/
/* Private: R e s e t */
/******************************************************************************/
void XrdSsiFileSess::Reset()
{
// Close this session
//
if (isOpen) close(true);
// Release other buffers
//
if (tident) free(tident);
if (fsUser) free(fsUser);
if (gigID) free(gigID);
}
/******************************************************************************/
/* S e n d D a t a */
/******************************************************************************/
int XrdSsiFileSess::SendData(XrdSfsDio *sfDio,
XrdSfsFileOffset offset,
XrdSfsXferSize size)
{
static const char *epname = "SendData";
XrdSsiRRInfo rInfo(offset);
XrdSsiRRTableItem<XrdSsiFileReq> rqstP;
unsigned int reqID = rInfo.Id();
int rc;
// Find the request object
//
if (!(rqstP = rTab.LookUp(reqID)))
return XrdSsiUtils::Emsg(epname, ESRCH, "send", gigID, *eInfo);
// Simply effect the send via the request object
//
rc = rqstP->Send(sfDio, size);
// Determine how this ended
//
if (rc > 0) rc = SFS_OK;
else rTab.DelFinalize(std::move(rqstP));
return rc;
}
/******************************************************************************/
/* t r u n c a t e */
/******************************************************************************/
int XrdSsiFileSess::truncate(XrdSfsFileOffset flen) // In
/*
Function: Set the length of the file object to 'flen' bytes.
Input: flen - The new size of the file.
Output: Returns SFS_ERROR a this function is not supported.
*/
{
static const char *epname = "trunc";
XrdSsiRRTableItem<XrdSsiFileReq> rqstP;
XrdSsiRRInfo rInfo(flen);
XrdSsiRRInfo::Opc reqXQ = rInfo.Cmd();
unsigned int reqID = rInfo.Id();
// Find the request object. If not there we may have encountered an eof
//
if (!(rqstP = rTab.LookUp(reqID)))
{if (eofVec.IsSet(reqID))
{eofVec.UnSet(reqID);
return 0;
}
return XrdSsiUtils::Emsg(epname, ESRCH, "cancel", gigID, *eInfo);
}
// Process request (this can only be a cancel request)
//
if (reqXQ != XrdSsiRRInfo::Can)
return XrdSsiUtils::Emsg(epname, ENOTSUP, "trunc", gigID, *eInfo);
// Perform the cancellation
//
DEBUG(reqID <<':' <<gigID <<" cancelled");
rTab.DelFinalize(std::move(rqstP));
return SFS_OK;
}
/******************************************************************************/
/* w r i t e */
/******************************************************************************/
XrdSfsXferSize XrdSsiFileSess::write(XrdSfsFileOffset offset, // In
const char *buff, // In
XrdSfsXferSize blen) // In
/*
Function: Write `blen' bytes at `offset' from 'buff' and return the actual
number of bytes written.
Input: offset - The absolute byte offset at which to start the write.
buff - Address of the buffer from which to get the data.
blen - The size of the buffer. This is the maximum number
of bytes that will be written to 'fd'.
Output: Returns the number of bytes written upon success and SFS_ERROR o/w.
Notes: An error return may be delayed until the next write(), close(), or
sync() call.
*/
{
static const char *epname = "write";
XrdSsiRRInfo rInfo(offset);
unsigned int reqID = rInfo.Id();
int reqPass;
// Check if we are reading a request segment and handle that. This assumes that
// writes to different requests cannot be interleaved (which they can't be).
//
if (inProg) return writeAdd(buff, blen, reqID);
// Make sure this request does not refer to an active request
//
if (rTab.LookUp(reqID))
return XrdSsiUtils::Emsg(epname, EADDRINUSE, "write", gigID, *eInfo);
// The offset contains the actual size of the request, make sure it's OK. Note
// that it can be zero and by convention the blen must be one if so.
//
reqPass = reqSize = rInfo.Size();
if (reqSize < blen)
{if (reqSize || blen != 1)
return XrdSsiUtils::Emsg(epname, EPROTO, "write", gigID, *eInfo);
reqSize = 1;
} else if (reqSize < 0 || reqSize > maxRSZ)
return XrdSsiUtils::Emsg(epname, EFBIG, "write", gigID, *eInfo);
// Indicate we are in the progress of collecting the request arguments
//
inProg = true;
eofVec.UnSet(reqID);
// Do some debugging
//
DEBUG(reqID <<':' <<gigID <<" rsz=" <<reqSize <<" wsz=" <<blen);
// If the complete request is here then grab the buffer, transfer ownership to
// the request object, and then activate it for processing.
//
if (reqSize == blen && xioP)
{XrdSfsXioHandle bRef = xioP->Claim(buff, reqSize, minRSZ);
if (!bRef)
{if (errno) Log.Emsg(epname,"Xio.Claim() failed;",XrdSysE2T(errno));}
else {if (!NewRequest(reqID, 0, bRef, reqPass))
return XrdSsiUtils::Emsg(epname,ENOMEM,"write xio",gigID,*eInfo);
return blen;
}
}
// The full request is not present, so get a buffer to piece it together
//
if (!(oucBuff = BuffPool->Alloc(reqSize)))
return XrdSsiUtils::Emsg(epname, ENOMEM, "write alloc", gigID, *eInfo);
// Setup to buffer this
//
reqLeft = reqSize - blen;
memcpy(oucBuff->Data(), buff, blen);
if (!reqLeft)
{oucBuff->SetLen(reqSize);
if (!NewRequest(reqID, oucBuff, 0, reqPass))
return XrdSsiUtils::Emsg(epname, ENOMEM, "write sfs", gigID, *eInfo);
oucBuff = 0;
} else oucBuff->SetLen(blen, blen);
return blen;
}
/******************************************************************************/
/* Private: w r i t e A d d */
/******************************************************************************/
XrdSfsXferSize XrdSsiFileSess::writeAdd(const char *buff, // In
XrdSfsXferSize blen, // In
unsigned int rid)
/*
Function: Add `blen' bytes from 'buff' to request and return the actual
number of bytes added.
Input: buff - Address of the buffer from which to get the data.
blen - The size of the buffer. This is the maximum number
of bytes that will be added.
Output: Returns the number of bytes added upon success and SFS_ERROR o/w.
Notes: An error return may be delayed until the next write(), close(), or
sync() call.
*/
{
static const char *epname = "writeAdd";
int dlen;
// Make sure the caller is not exceeding the size stated on the first write
//
if (blen > reqLeft)
return XrdSsiUtils::Emsg(epname, EFBIG, "writeAdd", gigID, *eInfo);
// Append the bytes
//
memcpy(oucBuff->Data(dlen), buff, blen);
// Adjust how much we have left
//
reqLeft -= blen;
DEBUG(rid <<':' <<gigID <<" rsz=" <<reqLeft <<" wsz=" <<blen);
// If we have a complete request. Transfer the buffer ownership to the request
// object and activate processing.
//
if (!reqLeft)
{oucBuff->SetLen(reqSize);
if (!NewRequest(rid, oucBuff, 0, reqSize))
return XrdSsiUtils::Emsg(epname, ENOMEM, "write", gigID, *eInfo);
oucBuff = 0;
} else {
dlen += blen;
oucBuff->SetLen(dlen, dlen);
}
// Return how much we appended
//
return blen;
}
tident
#define tident
Definition XrdBwmHandle.cc:109
DEBUG
#define DEBUG(x)
Definition XrdBwmTrace.hh:54
EPNAME
#define EPNAME(x)
Definition XrdBwmTrace.hh:56
QTRACE
#define QTRACE(act)
Definition XrdCmsTrace.hh:49
XrdNetAddrInfo.hh
XrdOucBuffer.hh
XrdOucERoute.hh
XrdOucEnv.hh
XrdOucPList.hh
close
#define close(a)
Definition XrdPosix.hh:48
XrdSecEntity.hh
Debug
bool Debug
Definition XrdSecgsiProxy.cc:95
Path
XrdOucString Path
Definition XrdSecpwdSrvAdmin.cc:160
XrdSfsAio.hh
SFS_DATAVEC
#define SFS_DATAVEC
Definition XrdSfsInterface.hh:113
SFS_ERROR
#define SFS_ERROR
Definition XrdSfsInterface.hh:109
SFS_REDIRECT
#define SFS_REDIRECT
Definition XrdSfsInterface.hh:110
SFS_STARTED
#define SFS_STARTED
Definition XrdSfsInterface.hh:111
XrdSfsFileOpenMode
int XrdSfsFileOpenMode
Definition XrdSfsInterface.hh:129
SFS_FCTL_SPEC1
#define SFS_FCTL_SPEC1
Definition XrdSfsInterface.hh:88
SFS_OK
#define SFS_OK
Definition XrdSfsInterface.hh:108
XrdSfsFileOffset
long long XrdSfsFileOffset
Definition XrdSfsInterface.hh:128
XrdSfsXferSize
int XrdSfsXferSize
Definition XrdSfsInterface.hh:131
XrdSfsXioHandle
class XrdBuffer * XrdSfsXioHandle
Definition XrdSfsXio.hh:46
XrdSsiEntity.hh
DUMPIT
#define DUMPIT(x, y)
Definition XrdSsiFileReq.cc:58
XrdSsiFileSess.hh
XrdSsiProvider.hh
XrdSsiRRInfo.hh
XrdSsiService.hh
XrdSsiSfs.hh
XrdSsiStats.hh
XrdSsiStream.hh
XrdSsiTrace.hh
XrdSsiUtils.hh
XrdSysE2T
const char * XrdSysE2T(int errcode)
Definition XrdSysE2T.cc:104
XrdSysE2T.hh
XrdSysError.hh
XrdOucBuffer
Definition XrdOucBuffer.hh:141
XrdOucBuffer::Data
char * Data() const
Definition XrdOucBuffer.hh:181
XrdOucBuffer::SetLen
void SetLen(int dataL, int dataO=0)
Definition XrdOucBuffer.hh:241
XrdOucEICB
Definition XrdOucErrInfo.hh:483
XrdOucEnv
Definition XrdOucEnv.hh:42
XrdOucErrInfo
Definition XrdOucErrInfo.hh:101
XrdSecEntity
Definition XrdSecEntity.hh:65
XrdSfsDio
Definition XrdSfsDio.hh:47
XrdSsiBVec::Reset
void Reset()
Definition XrdSsiBVec.hh:55
XrdSsiErrInfo
Definition XrdSsiErrInfo.hh:41
XrdSsiFileReq::Alloc
static XrdSsiFileReq * Alloc(XrdOucErrInfo *eP, XrdSsiFileResource *rP, XrdSsiFileSess *fP, const char *sn, const char *id, unsigned int rnum)
Definition XrdSsiFileReq.cc:219
XrdSsiFileSess
Definition XrdSsiFileSess.hh:47
XrdSsiFileSess::fctl
int fctl(const int cmd, int alen, const char *args, const XrdSecEntity *client)
Definition XrdSsiFileSess.cc:293
XrdSsiFileSess::open
int open(const char *fileName, XrdOucEnv &theEnv, XrdSfsFileOpenMode openMode)
Definition XrdSsiFileSess.cc:403
XrdSsiFileSess::close
int close(bool viaDel=false)
Definition XrdSsiFileSess.cc:250
XrdSsiFileSess::write
XrdSfsXferSize write(XrdSfsFileOffset fileOffset, const char *buffer, XrdSfsXferSize buffer_size)
Definition XrdSsiFileSess.cc:666
XrdSsiFileSess::AttnInfo
bool AttnInfo(XrdOucErrInfo &eInfo, const XrdSsiRespInfo *respP, unsigned int reqID)
Definition XrdSsiFileSess.cc:160
XrdSsiFileSess::read
XrdSfsXferSize read(XrdSfsFileOffset fileOffset, char *buffer, XrdSfsXferSize buffer_size)
Definition XrdSsiFileSess.cc:496
XrdSsiFileSess::truncate
int truncate(XrdSfsFileOffset fileOffset)
Definition XrdSsiFileSess.cc:625
XrdSsiFileSess::errInfo
XrdOucErrInfo * errInfo()
Definition XrdSsiFileSess.hh:62
XrdSsiFileSess::SendData
int SendData(XrdSfsDio *sfDio, XrdSfsFileOffset offset, XrdSfsXferSize size)
Definition XrdSsiFileSess.cc:594
XrdSsiFileSess::Recycle
void Recycle()
Definition XrdSsiFileSess.cc:548
XrdSsiFileSess::Alloc
static XrdSsiFileSess * Alloc(XrdOucErrInfo &einfo, const char *user)
Definition XrdSsiFileSess.cc:126
XrdSsiRRInfo
Definition XrdSsiRRInfo.hh:38
XrdSsiRRInfo::Opc
Opc
Definition XrdSsiRRInfo.hh:43
XrdSsiRRInfo::Can
@ Can
Definition XrdSsiRRInfo.hh:43
XrdSsiRRInfo::Size
void Size(unsigned int sz)
Definition XrdSsiRRInfo.hh:60
XrdSsiRRInfo::Cmd
void Cmd(Opc cmd)
Definition XrdSsiRRInfo.hh:45
XrdSsiRRInfo::Id
void Id(unsigned int id)
Definition XrdSsiRRInfo.hh:52
XrdSsiRRTableItem
Definition XrdSsiRRTable.hh:43
XrdSsiRRTable::Clear
void Clear()
Definition XrdSsiRRTable.hh:105
XrdSsiResponder::MaxDirectXfr
static const int MaxDirectXfr
Definition XrdSsiResponder.hh:81
XrdSsiService
Definition XrdSsiService.hh:55
XrdSsiStats
Definition XrdSsiStats.hh:38
XrdSsiUtils::Emsg
static int Emsg(const char *pfx, int ecode, const char *op, const char *path, XrdOucErrInfo &eDest)
Definition XrdSsiUtils.cc:159
XrdSysError
Definition XrdSysError.hh:90
XrdSysMutex
Definition XrdSysPthread.hh:165
XrdSsi
Definition XrdSsiClient.cc:65
XrdSsi::Stats
XrdSsiStats Stats
Definition XrdSsiFileReq.cc:69
XrdSsi::minRSZ
int minRSZ
Definition XrdSsiSfsConfig.cc:103
XrdSsi::respWT
int respWT
Definition XrdSsiSfsConfig.cc:101
XrdSsi::Provider
XrdSsiProvider * Provider
Definition XrdSsiService.cc:39
XrdSsi::BuffPool
XrdOucBuffPool * BuffPool
Definition XrdSsiSfsConfig.cc:89
XrdSsi::Service
XrdSsiService * Service
Definition XrdSsiFileSess.cc:72
XrdSsi::Log
XrdSysError Log
Definition XrdSsiFileReq.cc:66
XrdSsi::maxRSZ
int maxRSZ
Definition XrdSsiSfsConfig.cc:104
XrdSsiRRInfoAttn
Definition XrdSsiRRInfo.hh:90
XrdSsiRRInfoAttn::fullResp
static const int fullResp
Definition XrdSsiRRInfo.hh:92
XrdSsiRRInfoAttn::pendResp
static const int pendResp
Definition XrdSsiRRInfo.hh:93
XrdSsiRespInfo
Definition XrdSsiRespInfo.hh:44
XrdSsiRespInfo::isData
@ isData
Definition XrdSsiRespInfo.hh:58
XrdSsiRespInfo::rType
Resp_t rType
Definition XrdSsiRespInfo.hh:59
XrdSsiRespInfo::mdlen
int mdlen
Metadata length.
Definition XrdSsiRespInfo.hh:55
XrdSsiRespInfo::mdata
const char * mdata
-> Metadata about response.
Definition XrdSsiRespInfo.hh:56