Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Example of proposed XrdOss advanced error interface usage #1915

Closed
wants to merge 3 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
40 changes: 39 additions & 1 deletion src/XrdOfs/XrdOfs.cc
Original file line number Diff line number Diff line change
Expand Up @@ -737,7 +737,7 @@ int XrdOfsFile::open(const char *path, // In
}
if (XrdOfsFS->Balancer && retc == -ENOENT)
XrdOfsFS->Balancer->Removed(path);
return XrdOfsFS->Emsg(epname, error, retc, "open", path);
return XrdOfsFS->Emsg(epname, error, retc, "open", path, oP.fP);
}

// Verify that we can actually use this file
Expand Down Expand Up @@ -2555,6 +2555,44 @@ int XrdOfs::Emsg(const char *pfx, // Message prefix value
return SFS_ERROR;
}

/******************************************************************************/

int XrdOfs::Emsg(const char *pfx, // Message prefix value
XrdOucErrInfo &einfo, // Place to put text & error code
int ecode, // The error code
const char *op, // Operation being performed
const char *target, // The target (e.g., fname)
const XrdOssDF *fP) // The file object generating this error
{
char buffer[MAXPATHLEN+80];

// If the error is EBUSY then we just need to stall the client. This is
// a hack in order to provide for proxy support
//
if (ecode < 0) ecode = -ecode;
if (ecode == EBUSY) return 5; // A hack for proxy support

// Check for timeout conditions that require a client delay
//
if (ecode == ETIMEDOUT) return OSSDelay;

// Format the error message
//
XrdOucERoute::Format(buffer, sizeof(buffer), ecode, op, target);

// Print it out if debugging is enabled
//
#ifndef NODEBUG
OfsEroute.Emsg(pfx, einfo.getErrUser(), buffer);
#endif

// Place the error message in the error object and return
//
const XrdOucErrInfo *chainedErr = (OssHasErr && fP) ? fP->getError() : nullptr;
einfo.setErrInfo(ecode, buffer, chainedErr);
return SFS_ERROR;
}

/******************************************************************************/
/* P R I V A T E S E C T I O N */
/******************************************************************************/
Expand Down
3 changes: 3 additions & 0 deletions src/XrdOfs/XrdOfs.hh
Original file line number Diff line number Diff line change
Expand Up @@ -433,6 +433,8 @@ static int Emsg(const char *, XrdOucErrInfo &, int, const char *x,
XrdOfsHandle *hP);
static int Emsg(const char *, XrdOucErrInfo &, int, const char *x,
const char *y="");
int Emsg(const char *, XrdOucErrInfo &, int, const char *opName,
const char *path, const XrdOssDF *fP);
static int fsError(XrdOucErrInfo &myError, int rc);
const char *Split(const char *Args, const char **Opq, char *Path, int Plen);
int Stall(XrdOucErrInfo &, int, const char *);
Expand Down Expand Up @@ -480,6 +482,7 @@ XrdSysMutex ocMutex; // Global mutex for open/close
bool DirRdr; // Opendir() can be redirected.
bool reProxy; // Reproxying required for TPC
bool OssHasPGrw; // True: oss implements full rgRead/Write
bool OssHasErr; // True if the OSS can produce error messages

/******************************************************************************/
/* O t h e r D a t a */
Expand Down
4 changes: 4 additions & 0 deletions src/XrdOfs/XrdOfsConfig.cc
Original file line number Diff line number Diff line change
Expand Up @@ -357,6 +357,10 @@ int XrdOfs::Configure(XrdSysError &Eroute, XrdOucEnv *EnvInfo) {
//
OssHasPGrw = (ossFeatures & XRDOSS_HASPGRW) != 0;

// Indicate whether the oss implementation has getError for additional error
// message information.
OssHasErr = (ossFeatures & XRDOSS_HASAERR);

// If POSC processing is enabled (as by default) do it. Warning! This must be
// the last item in the configuration list as we need a working filesystem.
// Note that in proxy mode we always disable posc!
Expand Down
16 changes: 16 additions & 0 deletions src/XrdOss/XrdOss.cc
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,14 @@ int XrdOss::FSctl(int cmd, int alen, const char *args, char **resp)
return -ENOTSUP;
}

/******************************************************************************/
/* g e t E r r o r */
/******************************************************************************/
const XrdOucErrInfo *XrdOss::getError() const
{
return nullptr;
}

/******************************************************************************/
/* R e l o c */
/******************************************************************************/
Expand Down Expand Up @@ -153,6 +161,14 @@ int XrdOssDF::Fctl(int cmd, int alen, const char *args, char **resp)
return -ENOTSUP;
}

/******************************************************************************/
/* g e t E r r o r */
/******************************************************************************/
const XrdOucErrInfo *XrdOssDF::getError() const
{
return nullptr;
}

/******************************************************************************/
/* p g R e a d */
/******************************************************************************/
Expand Down
35 changes: 35 additions & 0 deletions src/XrdOss/XrdOss.hh
Original file line number Diff line number Diff line change
Expand Up @@ -39,10 +39,12 @@
#include <sys/types.h>
#include <cstring>

#include "XrdVersion.hh"
#include "XrdOss/XrdOssVS.hh"
#include "XrdOuc/XrdOucIOVec.hh"

class XrdOucEnv;
class XrdOucErrInfo;
class XrdSysLogger;
class XrdSfsAio;

Expand Down Expand Up @@ -447,6 +449,21 @@ const char *getTID() {return tident;}

virtual ~XrdOssDF() {}

//-----------------------------------------------------------------------------
//! Return advanced error information about the last error encountered by
//! this object. Only invoked if the XrdOSS indicates it has feature XRDOSS_AERR
//! The advanced error feature provides the ability for more error information
//! than is possible from the typical error code (e.g., unstructured error
//! messages).
//!
//! @return Error object associated with the last error. Caller does not own
//! the returned memory. Lifetime of the returned object is only guaranteed
//! until the next method call. May return nullptr even if an error occurred.
//-----------------------------------------------------------------------------

#if XrdMajorVNUM(XrdVNUMBER) > 5 || defined(__GNUC__)
virtual const XrdOucErrInfo *getError() const;
#endif

protected:

Expand Down Expand Up @@ -479,6 +496,7 @@ short rsvd; // Reserved
#define XRDOSS_HASCACH 0x0000000000000010ULL
#define XRDOSS_HASNAIO 0x0000000000000020ULL
#define XRDOSS_HASRPXY 0x0000000000000040ULL
#define XRDOSS_HASAERR 0x0000000000000080ULL

// Options that can be passed to Stat()
//
Expand Down Expand Up @@ -895,6 +913,23 @@ const char *Lfn2Pfn(const char *Path, char *buff, int blen, int &rc)

XrdOss() {}
virtual ~XrdOss() {}

//-----------------------------------------------------------------------------
//! Return advanced error information about the last error encountered by
//! this object. Only invoked if the XrdOSS indicates it has feature XRDOSS_AERR
//! The advanced error feature provides the ability for more error information
//! than is possible from the typical error code (e.g., unstructured error
//! messages).
//!
//! @return Error object associated with the last error. Caller does not own
//! the returned memory. Lifetime of the returned object is only guaranteed
//! until the next method call. May return nullptr even if an error occurred.
//-----------------------------------------------------------------------------

#if XrdMajorVNUM(XrdVNUMBER) > 5 || defined(__GNUC__)
virtual const XrdOucErrInfo *getError() const;
#endif

};

/******************************************************************************/
Expand Down
19 changes: 14 additions & 5 deletions src/XrdOuc/XrdOucErrInfo.hh
Original file line number Diff line number Diff line change
Expand Up @@ -138,14 +138,23 @@ inline int setErrCode(int code) {return ErrInfo.code = code;}
//-----------------------------------------------------------------------------
//! Set error code and error text.
//!
//! @param code - The error number describing the error.
//! @param emsg - The error message text.
//! @param code - The error number describing the error.
//! @param emsg - The error message text.
//! @param chainedErrInfo - Optionally, an error object triggering the current error
//!
//! @return code - The error number.
//-----------------------------------------------------------------------------

inline int setErrInfo(int code, const char *emsg)
{strlcpy(ErrInfo.message, emsg, sizeof(ErrInfo.message));
inline int setErrInfo(int code, const char *emsg, const XrdOucErrInfo *chainedErrInfo=nullptr)
{if (chainedErrInfo && chainedErrInfo->getErrText())
{const char *txtlist[4];
txtlist[0] = emsg;
txtlist[1] = " (";
txtlist[2] = chainedErrInfo->getErrText();
txtlist[3] = ")";
return setErrInfo(code, txtlist, 4);
}
strlcpy(ErrInfo.message, emsg, sizeof(ErrInfo.message));
if (dataBuff) {dataBuff->Recycle(); dataBuff = 0;}
return ErrInfo.code = code;
}
Expand Down Expand Up @@ -259,7 +268,7 @@ inline int getErrInfo(XrdOucEI &errParm)
//! @return The pointer to the internal error text.
//-----------------------------------------------------------------------------

inline const char *getErrText()
inline const char *getErrText() const
{if (dataBuff) return dataBuff->Data();
return (const char *)ErrInfo.message;
}
Expand Down
10 changes: 8 additions & 2 deletions src/XrdPss/XrdPss.cc
Original file line number Diff line number Diff line change
Expand Up @@ -157,7 +157,7 @@ XrdOss *XrdOssGetStorageSystem2(XrdOss *native_oss,

XrdPssSys::XrdPssSys() : LocalRoot(0), theN2N(0), DirFlags(0),
myVersion(&XrdVERSIONINFOVAR(XrdOssGetStorageSystem2)),
myFeatures(XRDOSS_HASPRXY|XRDOSS_HASPGRW|XRDOSS_HASNOSF)
myFeatures(XRDOSS_HASPRXY|XRDOSS_HASPGRW|XRDOSS_HASNOSF|XRDOSS_HASAERR)
{}

/******************************************************************************/
Expand Down Expand Up @@ -816,7 +816,13 @@ int XrdPssFile::Open(const char *path, int Oflag, mode_t Mode, XrdOucEnv &Env)
// Try to open and if we failed, return an error
//
if (!XrdPssSys::dcaCheck || !ioCache)
{if ((fd = XrdPosixXrootd::Open(pbuff,Oflag,Mode)) < 0) return -errno;
{if ((fd = XrdPosixXrootd::Open(pbuff,Oflag,Mode)) < 0)
{const char *txtlist[2];
txtlist[0] = "Failed to open file in cache: ";
txtlist[1] = XrdSysError::ec2text(errno);
errInfo.setErrInfo(errno, txtlist, 2);
return -errno;
}
} else {
XrdPosixInfo Info;
Info.ffReady = XrdPssSys::dcaWorld;
Expand Down
6 changes: 6 additions & 0 deletions src/XrdPss/XrdPss.hh
Original file line number Diff line number Diff line change
Expand Up @@ -35,6 +35,7 @@
#include <sys/types.h>
#include <vector>
#include "XrdSys/XrdSysHeaders.hh"
#include "XrdOuc/XrdOucErrInfo.hh"
#include "XrdOuc/XrdOucExport.hh"
#include "XrdOuc/XrdOucName2Name.hh"
#include "XrdOuc/XrdOucPList.hh"
Expand Down Expand Up @@ -85,6 +86,7 @@ int Fstat(struct stat *);
int Fsync();
int Fsync(XrdSfsAio *aiop);
int Ftruncate(unsigned long long);
const XrdOucErrInfo *getError() const override {return &errInfo;}
ssize_t pgRead (void* buffer, off_t offset, size_t rdlen,
uint32_t* csvec, uint64_t opts);
int pgRead (XrdSfsAio* aioparm, uint64_t opts);
Expand Down Expand Up @@ -125,6 +127,8 @@ struct tprInfo

char *tpcPath;
const XrdSecEntity *entity;

XrdOucErrInfo errInfo; // Error info object for advanced error reporting.
};

/******************************************************************************/
Expand Down Expand Up @@ -159,6 +163,7 @@ virtual
int Create(const char *, const char *, mode_t, XrdOucEnv &, int opts=0);
void EnvInfo(XrdOucEnv *envP);
uint64_t Features() {return myFeatures;}
const XrdOucErrInfo *getError() const override {return &errInfo;}
int Init(XrdSysLogger *, const char *) override {return -ENOTSUP;}
int Init(XrdSysLogger *, const char *, XrdOucEnv *envP) override;
int Lfn2Pfn(const char *Path, char *buff, int blen);
Expand Down Expand Up @@ -216,6 +221,7 @@ unsigned long long DirFlags; // Defaults for exports
XrdVersionInfo *myVersion;// -> Compilation version
XrdSecsssID *idMapper; // -> Auth ID mapper
uint64_t myFeatures;// Our feature set
XrdOucErrInfo errInfo; // Err info object for improved error message reporting

int Configure(const char *, XrdOucEnv *);
int ConfigProc(const char *ConfigFN);
Expand Down