File indexing completed on 2024-04-14 14:10:46

0001 //#     Filename:   SpatialException.cpp
0002 //#
0003 //#     Author:     John Doug Reynolds, P. Kunszt
0004 //#
0005 //#     Date:       Mar 1997
0006 //#
0007 //#     SPDX-FileCopyrightText: 2000 Peter Z. Kunszt Alex S. Szalay, Aniruddha R. Thakar
0008 //#                     The Johns Hopkins University
0009 //#
0010 //#     Modification history:
0011 //#
0012 //#     Oct. 1998, P. Kunszt : remove Rogue Wave C-string dependency
0013 //#                almost all the interface had to be rewritten.
0014 //#                Also, use some of the inheritance to avoid
0015 //#                code duplication. Introduced defaultstr[].
0016 //#     Oct 18, 2001 : Dennis C. Dinge -- Replaced ValVec with std::vector
0017 //#
0018 
0019 #include <cstdio>
0020 #include <cstdlib>
0021 #include <string.h>
0022 #include <SpatialException.h>
0023 
0024 /* --- SpatialException methods ------------------------------------------------- */
0025 const char *SpatialException::defaultstr[] = { "SDSS Science Archive",
0026                                                "generic exception",           // These specialized exceptions are
0027                                                "unimplemented functionality", // currently implemented. If no string
0028                                                "failed operation",            // is given, this is the standard
0029                                                "array bounds violation",      // message.
0030                                                "interface violation" };
0031 
0032 #define CONTEXT       0 // indices of exceptions
0033 #define GENERIC       1
0034 #define UNIMPLEMENTED 2
0035 #define FAILURE       3
0036 #define BOUNDS        4
0037 #define INTERFACE     5
0038 
0039 SpatialException::~SpatialException() throw()
0040 {
0041     clear();
0042 }
0043 
0044 SpatialException::SpatialException(const char *cstr, int defIndex) throw()
0045 {
0046     try
0047     {
0048         if (cstr)
0049         {
0050             str_ = new char[slen(cstr) + 1];
0051             strcpy(str_, cstr);
0052         }
0053         else
0054         {
0055             str_ = new char[50];
0056             sprintf(str_, "%s : %s", defaultstr[CONTEXT], defaultstr[defIndex]);
0057         }
0058     }
0059     catch (...)
0060     {
0061         clear();
0062     }
0063 }
0064 
0065 SpatialException::SpatialException(const char *context, const char *because, int defIndex) throw()
0066 {
0067     try
0068     {
0069         const char *tmpc, *tmpb;
0070         tmpc = context ? context : defaultstr[CONTEXT];
0071         tmpb = because ? because : defaultstr[defIndex];
0072         str_ = new char[slen(tmpc) + slen(tmpb) + 50]; // allow extensions
0073         sprintf(str_, "%s : %s", tmpc, tmpb);
0074     }
0075     catch (...)
0076     {
0077         clear();
0078     }
0079 }
0080 
0081 SpatialException::SpatialException(const SpatialException &oldX) throw()
0082 {
0083     try
0084     {
0085         if (oldX.str_)
0086         {
0087             str_ = new char[slen(oldX.str_) + 1];
0088             strcpy(str_, oldX.str_);
0089         }
0090     }
0091     catch (...)
0092     {
0093         clear();
0094     }
0095 }
0096 
0097 SpatialException &SpatialException::operator=(const SpatialException &oldX) throw()
0098 {
0099     try
0100     {
0101         if (&oldX != this) // beware of self-assignment
0102         {
0103             if (oldX.str_)
0104             {
0105                 str_ = new char[slen(oldX.str_) + 1];
0106                 strcpy(str_, oldX.str_);
0107             }
0108         }
0109     }
0110     catch (...)
0111     {
0112         clear();
0113     }
0114     return *this;
0115 }
0116 
0117 const char *SpatialException::what() const throw()
0118 {
0119     try
0120     {
0121         return str_;
0122     }
0123     catch (...)
0124     {
0125         return "";
0126     }
0127 }
0128 
0129 int SpatialException::slen(const char *str) const
0130 {
0131     if (str)
0132         return strlen(str);
0133     return 0;
0134 }
0135 
0136 void SpatialException::clear()
0137 {
0138     delete[] str_;
0139     str_ = nullptr;
0140 }
0141 /* --- SpatialUnimplemented methods --------------------------------------------- */
0142 
0143 SpatialUnimplemented::SpatialUnimplemented(const char *cstr) throw() : SpatialException(cstr, UNIMPLEMENTED)
0144 {
0145 }
0146 
0147 SpatialUnimplemented::SpatialUnimplemented(const char *context, const char *because) throw()
0148     : SpatialException(context, because, UNIMPLEMENTED)
0149 {
0150 }
0151 
0152 SpatialUnimplemented::SpatialUnimplemented(const SpatialUnimplemented &oldX) throw() : SpatialException(oldX)
0153 {
0154 }
0155 
0156 /* --- SpatialFailure methods --------------------------------------------------- */
0157 
0158 SpatialFailure::SpatialFailure(const char *cstr) throw() : SpatialException(cstr, FAILURE)
0159 {
0160 }
0161 
0162 SpatialFailure::SpatialFailure(const char *context, const char *because) throw()
0163     : SpatialException(context, because, FAILURE)
0164 {
0165 }
0166 
0167 SpatialFailure::SpatialFailure(const char *context, const char *operation, const char *resource,
0168                                const char *because) throw()
0169 {
0170     try
0171     {
0172         clear();
0173         if (!operation && !resource && !because)
0174         {
0175             if (!context)
0176                 context = defaultstr[CONTEXT];
0177             because = "failed operation";
0178         }
0179         size_t const len = slen(context) + slen(operation) + slen(resource) + slen(because) + 50;
0180         str_  = new char[len];
0181         *str_ = '\0';
0182         char * ptr = str_;
0183         if (!context)
0184             context = defaultstr[CONTEXT];
0185         ptr += sprintf(ptr, "%s: ", context);
0186         if (operation)
0187         {
0188             ptr += sprintf(ptr, " %s failed ", operation);
0189         }
0190         if (resource)
0191         {
0192             if (operation)
0193                 ptr += sprintf(ptr, " on \"%s\"", resource);
0194             else
0195                 ptr += sprintf(ptr, " trouble with \"%s\"", resource);
0196         }
0197         if (because)
0198         {
0199             if (operation || resource)
0200                 ptr += sprintf(ptr, " because %s", because);
0201             else
0202                 ptr += sprintf(ptr, " %s", because);
0203         }
0204     }
0205     catch (...)
0206     {
0207         clear();
0208     }
0209 }
0210 
0211 SpatialFailure::SpatialFailure(const SpatialFailure &oldX) throw() : SpatialException(oldX)
0212 {
0213 }
0214 
0215 /* --- SpatialBoundsError methods ----------------------------------------------- */
0216 
0217 SpatialBoundsError::SpatialBoundsError(const char *cstr) throw() : SpatialException(cstr, BOUNDS)
0218 {
0219 }
0220 
0221 SpatialBoundsError::SpatialBoundsError(const char *context, const char *array, int32 limit, int32 index) throw()
0222     : SpatialException(context, array, BOUNDS)
0223 {
0224     try
0225     {
0226         if (limit != -1)
0227         {
0228             char * ptr = str_;
0229             if (array)
0230                 ptr += sprintf(ptr, "[%d]", index);
0231             else
0232                 ptr += sprintf(ptr, " array index %d ", index);
0233             if (index > limit)
0234             {
0235                 ptr += sprintf(ptr, " over upper bound by %d", index - limit);
0236             }
0237             else
0238             {
0239                 ptr += sprintf(ptr, " under lower bound by %d", limit - index);
0240             }
0241         }
0242     }
0243     catch (...)
0244     {
0245         clear();
0246     }
0247 }
0248 
0249 SpatialBoundsError::SpatialBoundsError(const SpatialBoundsError &oldX) throw() : SpatialException(oldX)
0250 {
0251 }
0252 
0253 /* --- SpatialInterfaceError methods -------------------------------------------- */
0254 
0255 SpatialInterfaceError::SpatialInterfaceError(const char *cstr) throw() : SpatialException(cstr, INTERFACE)
0256 {
0257 }
0258 
0259 SpatialInterfaceError::SpatialInterfaceError(const char *context, const char *because) throw()
0260     : SpatialException(context, because, INTERFACE)
0261 {
0262 }
0263 
0264 SpatialInterfaceError::SpatialInterfaceError(const char *context, const char *argument, const char *because) throw()
0265 {
0266     try
0267     {
0268         clear();
0269         str_  = new char[slen(context) + slen(argument) + slen(because) + 128];
0270         *str_ = '\0';
0271         char * ptr = str_;
0272         if (!context)
0273             context = defaultstr[CONTEXT];
0274         ptr += sprintf(ptr, "%s: ", context);
0275         if (argument && because)
0276         {
0277             ptr += sprintf(ptr, " argument \"%s\" is invalid because %s ", argument, because);
0278         }
0279         else if (argument && !because)
0280         {
0281             ptr += sprintf(ptr, " invalid argument \"%s\" ", argument);
0282         }
0283         else if (!argument)
0284         {
0285             if (because)
0286                 ptr += sprintf(str_, " %s", because);
0287             else
0288                 ptr += sprintf(str_, " interface violation");
0289         }
0290     }
0291     catch (...)
0292     {
0293         clear();
0294     }
0295 }
0296 
0297 SpatialInterfaceError::SpatialInterfaceError(const SpatialInterfaceError &oldX) throw() : SpatialException(oldX)
0298 {
0299 }