1#include <db_cxx.h> 2 3/* 4 * Resource-acquisition-as-initialization pattern for Berkeley DB's cursors. 5 * 6 * Use DbcAuto instead of Berkeley DB's builtin Dbc class. The constructor 7 * allocates a new cursor, and it is freed automatically when it goes out of 8 * scope. 9 * 10 * Note that some care is required with the order in which Berkeley DB handles 11 * are closed. In particular, the cursor handle must be closed before any 12 * database or transaction handles the cursor references. In addition, the 13 * cursor close method can throw exceptions, which are masked by the destructor. 14 * 15 * For these reasons, you are strongly advised to call the DbcAuto::close 16 * method in the non-exceptional case. This class exists to ensure that 17 * cursors are closed if an exception occurs. 18 */ 19class DbcAuto { 20public: 21 DbcAuto(Db *db, DbTxn *txn, u_int32_t flags) { 22 db->cursor(txn, &dbc_, flags); 23 } 24 25 ~DbcAuto() { 26 try { 27 close(); 28 } catch(...) { 29 // Ignore it, another exception is pending 30 } 31 } 32 33 void close() { 34 if (dbc_) { 35 // Set the member to 0 before making the call in 36 // case an exception is thrown. 37 Dbc *tdbc = dbc_; 38 dbc_ = 0; 39 tdbc->close(); 40 } 41 } 42 43 operator Dbc *() { 44 return dbc_; 45 } 46 47 operator Dbc **() { 48 return &dbc_; 49 } 50 51 Dbc *operator->() { 52 return dbc_; 53 } 54 55private: 56 Dbc *dbc_; 57}; 58