use libc::c_int; use std::error::Error; use std::io::IoError; use std::str; use ffi; #[deriving(Show, Eq, PartialEq)] pub enum LmdbError { KeyExist, NotFound, PageNotFound, Corrupted, Panic, VersionMismatch, Invalid, MapFull, DbsFull, ReadersFull, TlsFull, TxnFull, CursorFull, PageFull, MapResized, Incompatible, BadRslot, BadTxn, BadValSize, BadDbi, Unknown(c_int), Io(IoError), } impl Error for LmdbError { fn description(&self) -> &str { let err_code = match *self { LmdbError::KeyExist => ffi::MDB_KEYEXIST, LmdbError::NotFound => ffi::MDB_NOTFOUND, LmdbError::PageNotFound => ffi::MDB_PAGE_NOTFOUND, LmdbError::Corrupted => ffi::MDB_CORRUPTED, LmdbError::Panic => ffi::MDB_PANIC, LmdbError::VersionMismatch => ffi::MDB_VERSION_MISMATCH, LmdbError::Invalid => ffi::MDB_INVALID, LmdbError::MapFull => ffi::MDB_MAP_FULL, LmdbError::DbsFull => ffi::MDB_DBS_FULL, LmdbError::ReadersFull => ffi::MDB_READERS_FULL, LmdbError::TlsFull => ffi::MDB_TLS_FULL, LmdbError::TxnFull => ffi::MDB_TXN_FULL, LmdbError::CursorFull => ffi::MDB_CURSOR_FULL, LmdbError::PageFull => ffi::MDB_PAGE_FULL, LmdbError::MapResized => ffi::MDB_MAP_RESIZED, LmdbError::Incompatible => ffi::MDB_INCOMPATIBLE, LmdbError::BadRslot => ffi::MDB_BAD_RSLOT, LmdbError::BadTxn => ffi::MDB_BAD_TXN, LmdbError::BadValSize => ffi::MDB_BAD_VALSIZE, LmdbError::BadDbi => ffi::MDB_BAD_DBI, LmdbError::Unknown(i) => i, LmdbError::Io(ref io_error) => return io_error.description(), }; unsafe { str::from_c_str(ffi::mdb_strerror(err_code) as *const _) } } } impl LmdbError { pub fn from_err_code(err_code: c_int) -> LmdbError { match err_code { i if i > 0 => LmdbError::Io(IoError::from_errno(err_code as uint, true)), ffi::MDB_KEYEXIST => LmdbError::KeyExist, ffi::MDB_NOTFOUND => LmdbError::NotFound, ffi::MDB_PAGE_NOTFOUND => LmdbError::PageNotFound, ffi::MDB_CORRUPTED => LmdbError::Corrupted, ffi::MDB_PANIC => LmdbError::Panic, ffi::MDB_VERSION_MISMATCH => LmdbError::VersionMismatch, ffi::MDB_INVALID => LmdbError::Invalid, ffi::MDB_MAP_FULL => LmdbError::MapFull, ffi::MDB_DBS_FULL => LmdbError::DbsFull, ffi::MDB_READERS_FULL => LmdbError::ReadersFull, ffi::MDB_TLS_FULL => LmdbError::TlsFull, ffi::MDB_TXN_FULL => LmdbError::TxnFull, ffi::MDB_CURSOR_FULL => LmdbError::CursorFull, ffi::MDB_PAGE_FULL => LmdbError::PageFull, ffi::MDB_MAP_RESIZED => LmdbError::MapResized, ffi::MDB_INCOMPATIBLE => LmdbError::Incompatible, ffi::MDB_BAD_RSLOT => LmdbError::BadRslot, ffi::MDB_BAD_TXN => LmdbError::BadTxn, ffi::MDB_BAD_VALSIZE => LmdbError::BadValSize, i => LmdbError::Unknown(i), } } } pub type LmdbResult = Result; pub fn lmdb_result(err_code: c_int) -> LmdbResult<()> { if err_code == ffi::MDB_SUCCESS { Ok(()) } else { Err(LmdbError::from_err_code(err_code)) } }