00001
00022 #ifndef HYPERTABLE_ERROR_H
00023 #define HYPERTABLE_ERROR_H
00024
00025 #include "Common/String.h"
00026 #include <ostream>
00027 #include <stdexcept>
00028
00029 namespace Hypertable {
00030 namespace Error {
00031 enum Code {
00032 UNPOSSIBLE = -3,
00033 EXTERNAL = -2,
00034 FAILED_EXPECTATION = -1,
00035 OK = 0,
00036 PROTOCOL_ERROR = 1,
00037 REQUEST_TRUNCATED = 2,
00038 RESPONSE_TRUNCATED = 3,
00039 REQUEST_TIMEOUT = 4,
00040 LOCAL_IO_ERROR = 5,
00041 BAD_ROOT_LOCATION = 6,
00042 BAD_SCHEMA = 7,
00043 INVALID_METADATA = 8,
00044 BAD_KEY = 9,
00045 METADATA_NOT_FOUND = 10,
00046 HQL_PARSE_ERROR = 11,
00047 FILE_NOT_FOUND = 12,
00048 BLOCK_COMPRESSOR_UNSUPPORTED_TYPE = 13,
00049 BLOCK_COMPRESSOR_INVALID_ARG = 14,
00050 BLOCK_COMPRESSOR_TRUNCATED = 15,
00051 BLOCK_COMPRESSOR_BAD_HEADER = 16,
00052 BLOCK_COMPRESSOR_BAD_MAGIC = 17,
00053 BLOCK_COMPRESSOR_CHECKSUM_MISMATCH = 18,
00054 BLOCK_COMPRESSOR_DEFLATE_ERROR = 19,
00055 BLOCK_COMPRESSOR_INFLATE_ERROR = 20,
00056 BLOCK_COMPRESSOR_INIT_ERROR = 21,
00057 TABLE_NOT_FOUND = 22,
00058 MALFORMED_REQUEST = 23,
00059 TOO_MANY_COLUMNS = 24,
00060 BAD_DOMAIN_NAME = 25,
00061 COMMAND_PARSE_ERROR = 26,
00062 CONNECT_ERROR_MASTER = 27,
00063 CONNECT_ERROR_HYPERSPACE = 28,
00064 BAD_MEMORY_ALLOCATION = 29,
00065 BAD_SCAN_SPEC = 30,
00066 NOT_IMPLEMENTED = 31,
00067 VERSION_MISMATCH = 32,
00068 CANCELLED = 33,
00069 SCHEMA_PARSE_ERROR = 34,
00070 SYNTAX_ERROR = 35,
00071 DOUBLE_UNGET = 36,
00072 EMPTY_BLOOMFILTER = 37,
00073 BLOOMFILTER_CHECKSUM_MISMATCH = 38,
00074 NAME_ALREADY_IN_USE = 39,
00075 NAMESPACE_DOES_NOT_EXIST = 40,
00076 BAD_NAMESPACE = 41,
00077 NAMESPACE_EXISTS = 42,
00078 NO_RESPONSE = 43,
00079 NOT_ALLOWED = 44,
00080 INDUCED_FAILURE = 45,
00081 SERVER_SHUTTING_DOWN = 46,
00082
00083 CONFIG_BAD_ARGUMENT = 1001,
00084 CONFIG_BAD_CFG_FILE = 1002,
00085 CONFIG_GET_ERROR = 1003,
00086 CONFIG_BAD_VALUE = 1004,
00087
00088 COMM_NOT_CONNECTED = 0x00010001,
00089 COMM_BROKEN_CONNECTION = 0x00010002,
00090 COMM_CONNECT_ERROR = 0x00010003,
00091 COMM_ALREADY_CONNECTED = 0x00010004,
00092
00093 COMM_SEND_ERROR = 0x00010006,
00094 COMM_RECEIVE_ERROR = 0x00010007,
00095 COMM_POLL_ERROR = 0x00010008,
00096 COMM_CONFLICTING_ADDRESS = 0x00010009,
00097 COMM_SOCKET_ERROR = 0x0001000A,
00098 COMM_BIND_ERROR = 0x0001000B,
00099 COMM_LISTEN_ERROR = 0x0001000C,
00100 COMM_HEADER_CHECKSUM_MISMATCH = 0x0001000D,
00101 COMM_PAYLOAD_CHECKSUM_MISMATCH = 0x0001000E,
00102 COMM_BAD_HEADER = 0x0001000F,
00103 COMM_INVALID_PROXY = 0x00010010,
00104
00105 DFSBROKER_BAD_FILE_HANDLE = 0x00020001,
00106 DFSBROKER_IO_ERROR = 0x00020002,
00107 DFSBROKER_FILE_NOT_FOUND = 0x00020003,
00108 DFSBROKER_BAD_FILENAME = 0x00020004,
00109 DFSBROKER_PERMISSION_DENIED = 0x00020005,
00110 DFSBROKER_INVALID_ARGUMENT = 0x00020006,
00111 DFSBROKER_INVALID_CONFIG = 0x00020007,
00112 DFSBROKER_EOF = 0x00020008,
00113
00114 HYPERSPACE_IO_ERROR = 0x00030001,
00115 HYPERSPACE_CREATE_FAILED = 0x00030002,
00116 HYPERSPACE_FILE_NOT_FOUND = 0x00030003,
00117 HYPERSPACE_ATTR_NOT_FOUND = 0x00030004,
00118 HYPERSPACE_DELETE_ERROR = 0x00030005,
00119 HYPERSPACE_BAD_PATHNAME = 0x00030006,
00120 HYPERSPACE_PERMISSION_DENIED = 0x00030007,
00121 HYPERSPACE_EXPIRED_SESSION = 0x00030008,
00122 HYPERSPACE_FILE_EXISTS = 0x00030009,
00123 HYPERSPACE_IS_DIRECTORY = 0x0003000A,
00124 HYPERSPACE_INVALID_HANDLE = 0x0003000B,
00125 HYPERSPACE_REQUEST_CANCELLED = 0x0003000C,
00126 HYPERSPACE_MODE_RESTRICTION = 0x0003000D,
00127 HYPERSPACE_ALREADY_LOCKED = 0x0003000E,
00128 HYPERSPACE_LOCK_CONFLICT = 0x0003000F,
00129 HYPERSPACE_NOT_LOCKED = 0x00030010,
00130 HYPERSPACE_BAD_ATTRIBUTE = 0x00030011,
00131 HYPERSPACE_BERKELEYDB_ERROR = 0x00030012,
00132 HYPERSPACE_DIR_NOT_EMPTY = 0x00030013,
00133 HYPERSPACE_BERKELEYDB_DEADLOCK = 0x00030014,
00134 HYPERSPACE_BERKELEYDB_REP_HANDLE_DEAD = 0x00030015,
00135 HYPERSPACE_FILE_OPEN = 0x00030016,
00136 HYPERSPACE_CLI_PARSE_ERROR = 0x00030017,
00137 HYPERSPACE_CREATE_SESSION_FAILED = 0x00030018,
00138 HYPERSPACE_NOT_MASTER_LOCATION = 0x00030019,
00139
00140 HYPERSPACE_STATEDB_ERROR = 0x0003001A,
00141 HYPERSPACE_STATEDB_DEADLOCK = 0x0003001B,
00142 HYPERSPACE_STATEDB_BAD_KEY = 0x0003001C,
00143 HYPERSPACE_STATEDB_BAD_VALUE = 0x0003001D,
00144 HYPERSPACE_STATEDB_ALREADY_DELETED = 0x0003001E,
00145 HYPERSPACE_STATEDB_EVENT_EXISTS = 0x0003001F,
00146 HYPERSPACE_STATEDB_EVENT_NOT_EXISTS = 0x00030020,
00147 HYPERSPACE_STATEDB_EVENT_ATTR_NOT_FOUND = 0x00030021,
00148 HYPERSPACE_STATEDB_SESSION_EXISTS = 0x00030022,
00149 HYPERSPACE_STATEDB_SESSION_NOT_EXISTS = 0x00030023,
00150 HYPERSPACE_STATEDB_SESSION_ATTR_NOT_FOUND = 0x00030024,
00151 HYPERSPACE_STATEDB_HANDLE_EXISTS = 0x00030025,
00152 HYPERSPACE_STATEDB_HANDLE_NOT_EXISTS = 0x00030026,
00153 HYPERSPACE_STATEDB_HANDLE_ATTR_NOT_FOUND = 0x00030027,
00154 HYPERSPACE_STATEDB_NODE_EXISTS = 0x00030028,
00155 HYPERSPACE_STATEDB_NODE_NOT_EXISTS = 0x00030029,
00156 HYPERSPACE_STATEDB_NODE_ATTR_NOT_FOUND = 0x0003002A,
00157
00158 MASTER_TABLE_EXISTS = 0x00040001,
00159 MASTER_BAD_SCHEMA = 0x00040002,
00160 MASTER_NOT_RUNNING = 0x00040003,
00161 MASTER_NO_RANGESERVERS = 0x00040004,
00162 MASTER_FILE_NOT_LOCKED = 0x00040005,
00163 MASTER_RANGESERVER_ALREADY_REGISTERED = 0x00040006,
00164 MASTER_BAD_COLUMN_FAMILY = 0x00040007,
00165 MASTER_SCHEMA_GENERATION_MISMATCH = 0x00040008,
00166 MASTER_LOCATION_ALREADY_ASSIGNED = 0x00040009,
00167 MASTER_LOCATION_INVALID = 0x0004000A,
00168 MASTER_OPERATION_IN_PROGRESS = 0x0004000B,
00169
00170 RANGESERVER_GENERATION_MISMATCH = 0x00050001,
00171 RANGESERVER_RANGE_ALREADY_LOADED = 0x00050002,
00172 RANGESERVER_RANGE_MISMATCH = 0x00050003,
00173 RANGESERVER_NONEXISTENT_RANGE = 0x00050004,
00174 RANGESERVER_OUT_OF_RANGE = 0x00050005,
00175 RANGESERVER_RANGE_NOT_FOUND = 0x00050006,
00176 RANGESERVER_INVALID_SCANNER_ID = 0x00050007,
00177 RANGESERVER_SCHEMA_PARSE_ERROR = 0x00050008,
00178 RANGESERVER_SCHEMA_INVALID_CFID = 0x00050009,
00179 RANGESERVER_INVALID_COLUMNFAMILY = 0x0005000A,
00180 RANGESERVER_TRUNCATED_COMMIT_LOG = 0x0005000B,
00181 RANGESERVER_NO_METADATA_FOR_RANGE = 0x0005000C,
00182 RANGESERVER_SHUTTING_DOWN = 0x0005000D,
00183 RANGESERVER_CORRUPT_COMMIT_LOG = 0x0005000E,
00184 RANGESERVER_UNAVAILABLE = 0x0005000F,
00185 RANGESERVER_REVISION_ORDER_ERROR = 0x00050010,
00186 RANGESERVER_ROW_OVERFLOW = 0x00050011,
00187 RANGESERVER_TABLE_NOT_FOUND = 0x00050012,
00188 RANGESERVER_BAD_SCAN_SPEC = 0x00050013,
00189 RANGESERVER_CLOCK_SKEW = 0x00050014,
00190 RANGESERVER_BAD_CELLSTORE_FILENAME = 0x00050015,
00191 RANGESERVER_CORRUPT_CELLSTORE = 0x00050016,
00192 RANGESERVER_TABLE_DROPPED = 0x00050017,
00193 RANGESERVER_UNEXPECTED_TABLE_ID = 0x00050018,
00194 RANGESERVER_RANGE_BUSY = 0x00050019,
00195 RANGESERVER_BAD_CELL_INTERVAL = 0x0005001A,
00196 RANGESERVER_SHORT_CELLSTORE_READ = 0x0005001B,
00197
00198 HQL_BAD_LOAD_FILE_FORMAT = 0x00060001,
00199
00200 METALOG_VERSION_MISMATCH = 0x00070001,
00201 METALOG_BAD_RS_HEADER = 0x00070002,
00202 METALOG_BAD_HEADER = 0x00070003,
00203 METALOG_ENTRY_TRUNCATED = 0x00070004,
00204 METALOG_CHECKSUM_MISMATCH = 0x00070005,
00205 METALOG_ENTRY_BAD_TYPE = 0x00070006,
00206 METALOG_ENTRY_BAD_ORDER = 0x00070007,
00207
00208 SERIALIZATION_INPUT_OVERRUN = 0x00080001,
00209 SERIALIZATION_BAD_VINT = 0x00080002,
00210 SERIALIZATION_BAD_VSTR = 0x00080003,
00211
00212 THRIFTBROKER_BAD_SCANNER_ID = 0x00090001,
00213 THRIFTBROKER_BAD_MUTATOR_ID = 0x00090002,
00214 THRIFTBROKER_BAD_NAMESPACE_ID = 0x00090003,
00215 THRIFTBROKER_BAD_FUTURE_ID = 0x00090004
00216
00217 };
00218
00219 const char *get_text(int error);
00220
00221 }
00222
00223
00224 class Exception;
00225
00226
00227 struct ExceptionMessageRenderer {
00228 ExceptionMessageRenderer(const Exception &e) : ex(e) { }
00229
00230 std::ostream &render(std::ostream &out) const;
00231
00232 const Exception &ex;
00233 };
00234
00235 struct ExceptionMessagesRenderer {
00236 ExceptionMessagesRenderer(const Exception &e, const char *sep = ": ")
00237 : ex(e), separator(sep) { }
00238
00239 std::ostream &render(std::ostream &out) const;
00240
00241 const Exception &ex;
00242 const char *separator;
00243 };
00244
00249 class Exception : public std::runtime_error {
00250 const Exception &operator=(const Exception &);
00251
00252 int m_error;
00253 int m_line;
00254 const char *m_func;
00255 const char *m_file;
00256
00257 public:
00258 typedef std::runtime_error Parent;
00259
00260 Exception(int error, int l = 0, const char *fn = 0, const char *fl = 0)
00261 : Parent(""), m_error(error), m_line(l), m_func(fn), m_file(fl), prev(0)
00262 { }
00263 Exception(int error, const String &msg, int l = 0, const char *fn = 0,
00264 const char *fl = 0)
00265 : Parent(msg), m_error(error), m_line(l), m_func(fn), m_file(fl), prev(0)
00266 { }
00267 Exception(int error, const String &msg, const Exception &ex,
00268 int l = 0, const char *fn = 0, const char *fl = 0)
00269 : Parent(msg), m_error(error), m_line(l), m_func(fn), m_file(fl),
00270 prev(new Exception(ex)) { }
00271
00272 Exception(const Exception &ex) : Parent(ex), m_error(ex.m_error),
00273 m_line(ex.m_line), m_func(ex.m_func), m_file(ex.m_file) {
00274 prev = ex.prev ? new Exception(*ex.prev) : 0;
00275 }
00276 ~Exception() throw() { delete prev; prev = 0; }
00277
00278 int code() const { return m_error; }
00279 int line() const { return m_line; }
00280 const char *func() const { return m_func; }
00281 const char *file() const { return m_file; }
00282
00283
00284 virtual std::ostream &render_message(std::ostream &out) const {
00285 return out << what();
00286 }
00287
00288
00289 virtual std::ostream &
00290 render_messages(std::ostream &out, const char *sep) const;
00291
00292 ExceptionMessageRenderer message() const {
00293 return ExceptionMessageRenderer(*this);
00294 }
00295
00296 ExceptionMessagesRenderer messages(const char *sep = ": ") const {
00297 return ExceptionMessagesRenderer(*this, sep);
00298 }
00299
00300 Exception *prev;
00301 };
00302
00303 std::ostream &operator<<(std::ostream &out, const Exception &);
00304
00305 inline std::ostream &
00306 ExceptionMessageRenderer::render(std::ostream &out) const {
00307 return ex.render_message(out);
00308 }
00309
00310 inline std::ostream &
00311 ExceptionMessagesRenderer::render(std::ostream &out) const {
00312 return ex.render_messages(out, separator);
00313 }
00314
00315 inline std::ostream &
00316 operator<<(std::ostream &out, const ExceptionMessageRenderer &r) {
00317 return r.render(out);
00318 }
00319
00320 inline std::ostream &
00321 operator<<(std::ostream &out, const ExceptionMessagesRenderer &r) {
00322 return r.render(out);
00323 }
00324
00328 #define HT_EXCEPTION(_code_, _msg_) \
00329 Exception(_code_, _msg_, __LINE__, HT_FUNC, __FILE__)
00330
00331 #define HT_EXCEPTION2(_code_, _ex_, _msg_) \
00332 Exception(_code_, _msg_, _ex_, __LINE__, HT_FUNC, __FILE__)
00333
00334 #define HT_THROW(_code_, _msg_) throw HT_EXCEPTION(_code_, _msg_)
00335 #define HT_THROW_(_code_) HT_THROW(_code_, "")
00336 #define HT_THROW2(_code_, _ex_, _msg_) throw HT_EXCEPTION2(_code_, _ex_, _msg_)
00337 #define HT_THROW2_(_code_, _ex_) HT_THROW2(_code_, _ex_, "")
00338
00339 #define HT_THROWF(_code_, _fmt_, ...) \
00340 throw HT_EXCEPTION(_code_, format(_fmt_, __VA_ARGS__))
00341
00342 #define HT_THROW2F(_code_, _ex_, _fmt_, ...) \
00343 throw HT_EXCEPTION2(_code_, _ex_, format(_fmt_, __VA_ARGS__))
00344
00345 #define HT_RETHROWF(_fmt_, ...) \
00346 catch (Exception &e) { HT_THROW2F(e.code(), e, _fmt_, __VA_ARGS__); } \
00347 catch (std::bad_alloc &e) { \
00348 HT_THROWF(Error::BAD_MEMORY_ALLOCATION, _fmt_, __VA_ARGS__); \
00349 } \
00350 catch (std::exception &e) { \
00351 HT_THROWF(Error::EXTERNAL, "caught std::exception: %s " _fmt_, e.what(), \
00352 __VA_ARGS__); \
00353 } \
00354 catch (...) { \
00355 HT_ERRORF("caught unknown exception " _fmt_, __VA_ARGS__); \
00356 throw; \
00357 }
00358
00359 #define HT_RETHROW(_s_) HT_RETHROWF("%s", _s_)
00360 #define HT_RETHROW_ HT_RETHROW("")
00361
00362 #define HT_TRY(_s_, _code_) do { \
00363 try { _code_; } \
00364 HT_RETHROW(_s_) \
00365 } while (0)
00366
00367
00368
00369 #define HT_LOG_EXCEPTION(_s_) \
00370 catch (Exception &e) { HT_ERROR_OUT << e <<", "<< _s_ << HT_END; } \
00371 catch (std::bad_alloc &e) { \
00372 HT_ERROR_OUT <<"Out of memory, "<< _s_ << HT_END; } \
00373 catch (std::exception &e) { \
00374 HT_ERROR_OUT <<"Caught exception: "<< e.what() <<", "<< _s_ << HT_END; } \
00375 catch (...) { \
00376 HT_ERROR_OUT <<"Caught unknown exception, "<< _s_ << HT_END; }
00377
00378 #define HT_TRY_OR_LOG(_s_, _code_) do { \
00379 try { _code_; } \
00380 HT_LOG_EXCEPTION(_s_) \
00381 } while (0)
00382
00383
00384 }
00385
00386 #endif // HYPERTABLE_ERROR_H