Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2021-06-11 04:37:10

0001 // ----------------------------------------------------------------------
0002 //
0003 // ErrorObj.cc
0004 //
0005 // History:
0006 //
0007 // Created 7/8/98 mf
0008 // 6/16/99  mf, jvr     ErrorObj::operator<<( void (* f)(ErrorLog &) )
0009 //                      allows an "ErrorObj << endmsg;"
0010 // 7/16/99  jvr         Added setSeverity() and setID functions
0011 // 6/7/00   web         Forbid setting extreme severities; guard against
0012 //                      too-long ID's
0013 // 9/21/00  mf          Added copy constructor for use by ELerrorList
0014 // 5/7/01   mf          operator<< (const char[])
0015 // 6/5/01   mf          setReactedTo
0016 // 11/01/01 web         maxIDlength now unsigned
0017 //
0018 // 2/14/06  mf      Removed oerator<<(endmsg) which is not needed for
0019 //          MessageLogger for CMS
0020 //
0021 // 3/13/06  mf      Instrumented for automatic suppression of spaces.
0022 // 3/20/06  mf      Instrumented for universal suppression of spaces
0023 //          (that is, items no longer contain any space added
0024 //          by the MessageLogger stack)
0025 //
0026 // 4/28/06  mf      maxIDlength changed from 20 to 200
0027 //          If a category name exceeds that, then the
0028 //          limit not taking effect bug will occur again...
0029 //
0030 // 6/6/06  mf       verbatim
0031 //
0032 // ErrorObj( const ELseverityLevel & sev, const ELstring & id )
0033 // ~ErrorObj()
0034 // set( const ELseverityLevel & sev, const ELstring & id )
0035 // clear()
0036 // setModule    ( const ELstring & module )
0037 // setSubroutine( const ELstring & subroutine )
0038 // emitToken( const ELstring & txt )
0039 //
0040 // ----------------------------------------------------------------------
0041 
0042 #include <algorithm>
0043 #include <atomic>
0044 #include <cctype>
0045 
0046 #include "FWCore/MessageLogger/interface/ErrorObj.h"
0047 #include "FWCore/Utilities/interface/thread_safety_macros.h"
0048 
0049 #ifndef IOSTREAM_INCLUDED
0050 #endif
0051 
0052 // ----------------------------------------------------------------------
0053 
0054 // Possible Traces
0055 // #define ErrorObjCONSTRUCTOR_TRACE
0056 // #define ErrorObj_EMIT_TRACE
0057 // #define ErrorObj_SUB_TRACE
0058 
0059 // ----------------------------------------------------------------------
0060 
0061 namespace {
0062   bool eq_nocase(std::string_view a, std::string_view b) {
0063     return std::equal(
0064         a.begin(), a.end(), b.begin(), b.end(), [](char x, char y) { return std::toupper(x) == std::toupper(y); });
0065   }
0066 }  // namespace
0067 
0068 namespace edm {
0069 
0070   // ----------------------------------------------------------------------
0071   // Class static and class-wide parameter:
0072   // ----------------------------------------------------------------------
0073 
0074   // ---  class-wide serial number stamper:
0075   //
0076   CMS_THREAD_SAFE static std::atomic<int> ourSerial(0);
0077   const unsigned int maxIDlength(200);  // changed 4/28/06 from 20
0078 
0079   // ----------------------------------------------------------------------
0080   // Birth/death:
0081   // ----------------------------------------------------------------------
0082 
0083   ErrorObj::ErrorObj(const messagelogger::ELseverityLevel& sev, std::string_view id, bool verbat) : verbatim(verbat) {
0084 #ifdef ErrorObjCONSTRUCTOR_TRACE
0085     std::cerr << "Constructor for ErrorObj\n";
0086 #endif
0087 
0088     clear();
0089     set(sev, id);
0090 
0091   }  // ErrorObj()
0092 
0093   ErrorObj::ErrorObj(const ErrorObj& orig)
0094       : mySerial(orig.mySerial),
0095         myXid(orig.myXid),
0096         myIdOverflow(orig.myIdOverflow),
0097         myTimestamp(orig.myTimestamp),
0098         myItems(orig.myItems),
0099         myReactedTo(orig.myReactedTo),
0100         myOs(),
0101         emptyString(),
0102         verbatim(orig.verbatim) {
0103 #ifdef ErrorObjCONSTRUCTOR_TRACE
0104     std::cerr << "Copy Constructor for ErrorObj\n";
0105 #endif
0106 
0107   }  // ErrorObj(ErrorObj)
0108 
0109   ErrorObj::~ErrorObj() {
0110 #ifdef ErrorObjCONSTRUCTOR_TRACE
0111     std::cerr << "Destructor for ErrorObj\n";
0112 #endif
0113 
0114   }  // ~ErrorObj()
0115 
0116   ErrorObj& ErrorObj::operator=(const ErrorObj& other) {
0117     ErrorObj temp(other);
0118     this->swap(temp);
0119     return *this;
0120   }
0121 
0122   void ErrorObj::swap(ErrorObj& other) {
0123     std::swap(mySerial, other.mySerial);
0124     std::swap(myXid, other.myXid);
0125     myIdOverflow.swap(other.myIdOverflow);
0126     std::swap(myTimestamp, other.myTimestamp);
0127     myItems.swap(other.myItems);
0128     std::swap(myReactedTo, other.myReactedTo);
0129     myContext.swap(other.myContext);
0130     std::string temp(other.myOs.str());
0131     other.myOs.str(myOs.str());
0132     myOs.str(temp);
0133     emptyString.swap(other.emptyString);
0134     std::swap(verbatim, other.verbatim);
0135   }
0136 
0137   // ----------------------------------------------------------------------
0138   // Accessors:
0139   // ----------------------------------------------------------------------
0140 
0141   int ErrorObj::serial() const { return mySerial; }
0142   const ELextendedID& ErrorObj::xid() const { return myXid; }
0143   const std::string& ErrorObj::idOverflow() const { return myIdOverflow; }
0144   time_t ErrorObj::timestamp() const { return myTimestamp; }
0145   const ELlist_string& ErrorObj::items() const { return myItems; }
0146   bool ErrorObj::reactedTo() const { return myReactedTo; }
0147   bool ErrorObj::is_verbatim() const { return verbatim; }
0148 
0149   const std::string& ErrorObj::context() const { return myContext; }
0150 
0151   std::string ErrorObj::fullText() const {
0152     std::string result;
0153     for (auto const& it : myItems)
0154       result += it;
0155     return result;
0156   }  // fullText()
0157 
0158   // ----------------------------------------------------------------------
0159   // Mutators:
0160   // ----------------------------------------------------------------------
0161 
0162   void ErrorObj::setSeverity(const messagelogger::ELseverityLevel& sev) {
0163     using namespace edm::messagelogger;
0164     myXid.severity = (sev <= ELzeroSeverity)      ? (ELseverityLevel)ELdebug
0165                      : (sev >= ELhighestSeverity) ? (ELseverityLevel)ELsevere
0166                                                   : sev;
0167   }
0168 
0169   void ErrorObj::setID(std::string_view id) {
0170     myXid.id = id.substr(0, maxIDlength);
0171     if (id.length() > maxIDlength)
0172       myIdOverflow = id.substr(maxIDlength, id.length() - maxIDlength);
0173   }
0174 
0175   void ErrorObj::setModule(std::string_view module) { myXid.module = module; }
0176 
0177   void ErrorObj::setContext(std::string_view c) { myContext = c; }
0178 
0179   void ErrorObj::setSubroutine(std::string_view subroutine) {
0180 #ifdef ErrorObj_SUB_TRACE
0181     std::cerr << "=:=:=: ErrorObj::setSubroutine(" << subroutine << ")\n";
0182 #endif
0183     myXid.subroutine = (subroutine[0] == ' ') ? subroutine.substr(1) : subroutine;
0184   }
0185 
0186   void ErrorObj::setReactedTo(bool r) { myReactedTo = r; }
0187 
0188 #ifdef ErrorObj_SUB_TRACE
0189   static int subN = 0;
0190 #endif
0191 
0192   ErrorObj& ErrorObj::emitToken(std::string_view s) {
0193 #ifdef ErrorObj_EMIT_TRACE
0194     std::cerr << "=:=:=: ErrorObj::emitToken( " << s << " )\n";
0195 #endif
0196 
0197 #ifdef ErrorObj_SUB_TRACE
0198     if (subN > 0) {
0199       std::cerr << "=:=:=: subN ErrorObj::emitToken( " << s << " )\n";
0200       subN--;
0201     }
0202 #endif
0203 
0204     if (eq_nocase(s.substr(0, 5), "@SUB=")) {
0205 #ifdef ErrorObj_SUB_TRACE
0206       std::cerr << "=:=:=: ErrorObj::@SUB s.substr(5) is: " << s.substr(5) << '\n';
0207 #endif
0208       setSubroutine(s.substr(5));
0209     } else {
0210       myItems.emplace_back(s);
0211     }
0212 
0213     return *this;
0214 
0215   }  // emitToken()
0216 
0217   void ErrorObj::set(const messagelogger::ELseverityLevel& sev, std::string_view id) {
0218     clear();
0219 
0220     myTimestamp = time(nullptr);
0221     mySerial = ++ourSerial;
0222 
0223     setID(id);
0224     setSeverity(sev);
0225 
0226   }  // set()
0227 
0228   void ErrorObj::clear() {
0229     mySerial = 0;
0230     myXid.clear();
0231     myIdOverflow = "";
0232     myTimestamp = 0;
0233     myItems.erase(myItems.begin(), myItems.end());  // myItems.clear();
0234     myReactedTo = false;
0235 
0236   }  // clear()
0237 
0238   ErrorObj& ErrorObj::opltlt(const char s[]) {
0239     // Exactly equivalent to the general template.
0240     // If this is not provided explicitly, then the template will
0241     // be instantiated once for each length of string ever used.
0242     myOs.str(emptyString);
0243     myOs << s;
0244 #ifdef OLD_STYLE_AUTOMATIC_SPACES
0245     if (!myOs.str().empty()) {
0246       if (!verbatim) {
0247         emitToken(myOs.str() + ' ');
0248       } else {
0249         emitToken(myOs.str());
0250       }
0251     }
0252 #else
0253     if (!myOs.str().empty())
0254       emitToken(myOs.str());
0255 #endif
0256     return *this;
0257   }
0258 
0259   ErrorObj& operator<<(ErrorObj& e, const char s[]) { return e.opltlt(s); }
0260 
0261 }  // end of namespace edm  */