- Timestamp:
- Jan 4, 2011, 10:35:57 AM (15 years ago)
- Location:
- python/trunk
- Files:
-
- 4 edited
Legend:
- Unmodified
- Added
- Removed
-
python/trunk/Modules/_bsddb.c
r2 r132 74 74 * DBSequence (Sequence) 75 75 * 76 * More datatypes added: 77 * 78 * DBLogCursor (Log Cursor) 79 * 76 80 */ 77 81 … … 96 100 #undef COMPILING_BSDDB_C 97 101 98 static char *rcs_id = "$Id: _bsddb.c 78564 2010-03-01 21:08:21Z florent.xicluna$";102 static char *rcs_id = "$Id: _bsddb.c 81029 2010-05-09 14:46:46Z antoine.pitrou $"; 99 103 100 104 /* --------------------------------------------------------------------- */ … … 140 144 #if defined(MYDB_USE_GILSTATE) 141 145 #define MYDB_BEGIN_BLOCK_THREADS \ 142 146 PyGILState_STATE __savestate = PyGILState_Ensure(); 143 147 #define MYDB_END_BLOCK_THREADS \ 144 148 PyGILState_Release(__savestate); 145 149 #else /* MYDB_USE_GILSTATE */ 146 150 /* Pre GILState API - do it the long old way */ … … 169 173 170 174 #endif 171 172 /* Should DB_INCOMPLETE be turned into a warning or an exception? */173 #define INCOMPLETE_IS_WARNING 1174 175 175 176 /* --------------------------------------------------------------------- */ … … 192 193 static PyObject* DBSecondaryBadError; /* DB_SECONDARY_BAD */ 193 194 194 #if !INCOMPLETE_IS_WARNING195 static PyObject* DBIncompleteError; /* DB_INCOMPLETE */196 #endif197 198 195 static PyObject* DBInvalidArgError; /* EINVAL */ 199 196 static PyObject* DBAccessError; /* EACCES */ … … 209 206 static PyObject* DBRepHandleDeadError; /* DB_REP_HANDLE_DEAD */ 210 207 #endif 208 #if (DBVER >= 44) 209 static PyObject* DBRepLockoutError; /* DB_REP_LOCKOUT */ 210 #endif 211 212 #if (DBVER >= 46) 213 static PyObject* DBRepLeaseExpiredError; /* DB_REP_LEASE_EXPIRED */ 214 #endif 215 216 #if (DBVER >= 47) 217 static PyObject* DBForeignConflictError; /* DB_FOREIGN_CONFLICT */ 218 #endif 219 211 220 212 221 static PyObject* DBRepUnavailError; /* DB_REP_UNAVAIL */ 213 222 214 223 #if (DBVER < 43) 215 #define DB_BUFFER_SMALL ENOMEM 224 #define DB_BUFFER_SMALL ENOMEM 225 #endif 226 227 #if (DBVER < 48) 228 #define DB_GID_SIZE DB_XIDDATASIZE 216 229 #endif 217 230 … … 239 252 240 253 staticforward PyTypeObject DB_Type, DBCursor_Type, DBEnv_Type, DBTxn_Type, 241 DBLock_Type ;254 DBLock_Type, DBLogCursor_Type; 242 255 #if (DBVER >= 43) 243 256 staticforward PyTypeObject DBSequence_Type; … … 251 264 #define DBObject_Check(v) (Py_TYPE(v) == &DB_Type) 252 265 #define DBCursorObject_Check(v) (Py_TYPE(v) == &DBCursor_Type) 266 #define DBLogCursorObject_Check(v) (Py_TYPE(v) == &DBLogCursor_Type) 253 267 #define DBEnvObject_Check(v) (Py_TYPE(v) == &DBEnv_Type) 254 268 #define DBTxnObject_Check(v) (Py_TYPE(v) == &DBTxn_Type) … … 356 370 _CHECK_OBJECT_NOT_CLOSED(curs->dbc, DBCursorClosedError, DBCursor) 357 371 372 #define CHECK_LOGCURSOR_NOT_CLOSED(logcurs) \ 373 _CHECK_OBJECT_NOT_CLOSED(logcurs->logc, DBCursorClosedError, DBLogCursor) 374 358 375 #if (DBVER >= 43) 359 376 #define CHECK_SEQUENCE_NOT_CLOSED(curs) \ … … 538 555 srclen = strlen(src); 539 556 if (n <= 0) 540 557 return srclen; 541 558 copylen = (srclen > n-1) ? n-1 : srclen; 542 559 /* populate dest[0] thru dest[copylen-1] */ … … 555 572 #else 556 573 static void _db_errorCallback(const DB_ENV *db_env, 557 574 const char* prefix, const char* msg) 558 575 #endif 559 576 { … … 668 685 669 686 switch (err) { 670 case 0: /* successful, no error */ break; 671 672 #if (DBVER < 41) 673 case DB_INCOMPLETE: 674 #if INCOMPLETE_IS_WARNING 675 bytes_left = our_strlcpy(errTxt, db_strerror(err), sizeof(errTxt)); 676 /* Ensure that bytes_left never goes negative */ 677 if (_db_errmsg[0] && bytes_left < (sizeof(errTxt) - 4)) { 678 bytes_left = sizeof(errTxt) - bytes_left - 4 - 1; 679 assert(bytes_left >= 0); 680 strcat(errTxt, " -- "); 681 strncat(errTxt, _db_errmsg, bytes_left); 682 } 683 _db_errmsg[0] = 0; 684 exceptionRaised = PyErr_Warn(PyExc_RuntimeWarning, errTxt); 685 686 #else /* do an exception instead */ 687 errObj = DBIncompleteError; 688 #endif 689 break; 690 #endif /* DBVER < 41 */ 687 case 0: /* successful, no error */ 688 return 0; 691 689 692 690 case DB_KEYEMPTY: errObj = DBKeyEmptyError; break; … … 706 704 707 705 #if (DBVER >= 43) 708 709 706 /* ENOMEM and DB_BUFFER_SMALL were one and the same until 4.3 */ 707 case ENOMEM: errObj = PyExc_MemoryError; break; 710 708 #endif 711 709 case EINVAL: errObj = DBInvalidArgError; break; … … 720 718 #if (DBVER >= 42) 721 719 case DB_REP_HANDLE_DEAD : errObj = DBRepHandleDeadError; break; 720 #endif 721 #if (DBVER >= 44) 722 case DB_REP_LOCKOUT : errObj = DBRepLockoutError; break; 723 #endif 724 725 #if (DBVER >= 46) 726 case DB_REP_LEASE_EXPIRED : errObj = DBRepLeaseExpiredError; break; 727 #endif 728 729 #if (DBVER >= 47) 730 case DB_FOREIGN_CONFLICT : errObj = DBForeignConflictError; break; 722 731 #endif 723 732 … … 789 798 return -1; 790 799 } 791 self->haveStat = 0;792 800 return 0; 793 801 } … … 806 814 return -1; 807 815 } 808 self->haveStat = 0;809 816 return 0; 810 817 } … … 812 819 /* Get a key/data pair from a cursor */ 813 820 static PyObject* _DBCursor_get(DBCursorObject* self, int extra_flags, 814 821 PyObject *args, PyObject *kwargs, char *format) 815 822 { 816 823 int err; … … 823 830 824 831 if (!PyArg_ParseTupleAndKeywords(args, kwargs, format, kwnames, 825 &flags, &dlen, &doff)) 832 &flags, &dlen, &doff)) 826 833 return NULL; 827 834 … … 839 846 840 847 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 841 848 && self->mydb->moduleFlags.getReturnsNone) { 842 849 Py_INCREF(Py_None); 843 850 retval = Py_None; … … 883 890 { 884 891 PyObject* v; 885 892 /* if the value fits in regular int, use that. */ 886 893 #ifdef PY_LONG_LONG 887 888 889 890 #endif 891 894 if (sizeof(time_t) > sizeof(long)) 895 v = PyLong_FromLongLong((PY_LONG_LONG) value); 896 else 897 #endif 898 v = NUMBER_FromLong((long) value); 892 899 if (!v || PyDict_SetItemString(dict, name, v)) 893 900 PyErr_Clear(); … … 931 938 return NULL; 932 939 933 self->haveStat = 0;934 940 self->flags = 0; 935 941 self->setflags = 0; … … 1039 1045 INSERT_IN_DOUBLE_LINKED_LIST(self->mydb->children_cursors,self); 1040 1046 if (txn && ((PyObject *)txn!=Py_None)) { 1041 1042 1047 INSERT_IN_DOUBLE_LINKED_LIST_TXN(txn->children_cursors,self); 1048 self->txn=txn; 1043 1049 } else { 1044 1050 self->txn=NULL; 1045 1051 } 1046 1052 … … 1078 1084 1079 1085 1086 static DBLogCursorObject* 1087 newDBLogCursorObject(DB_LOGC* dblogc, DBEnvObject* env) 1088 { 1089 DBLogCursorObject* self; 1090 1091 self = PyObject_New(DBLogCursorObject, &DBLogCursor_Type); 1092 1093 if (self == NULL) 1094 return NULL; 1095 1096 self->logc = dblogc; 1097 self->env = env; 1098 1099 INSERT_IN_DOUBLE_LINKED_LIST(self->env->children_logcursors, self); 1100 1101 self->in_weakreflist = NULL; 1102 Py_INCREF(self->env); 1103 return self; 1104 } 1105 1106 1107 /* Forward declaration */ 1108 static PyObject *DBLogCursor_close_internal(DBLogCursorObject* self); 1109 1110 static void 1111 DBLogCursor_dealloc(DBLogCursorObject* self) 1112 { 1113 PyObject *dummy; 1114 1115 if (self->logc != NULL) { 1116 dummy = DBLogCursor_close_internal(self); 1117 /* 1118 ** Raising exceptions while doing 1119 ** garbage collection is a fatal error. 1120 */ 1121 if (dummy) 1122 Py_DECREF(dummy); 1123 else 1124 PyErr_Clear(); 1125 } 1126 if (self->in_weakreflist != NULL) { 1127 PyObject_ClearWeakRefs((PyObject *) self); 1128 } 1129 Py_DECREF(self->env); 1130 PyObject_Del(self); 1131 } 1132 1133 1080 1134 static DBEnvObject* 1081 1135 newDBEnvObject(int flags) … … 1093 1147 self->children_dbs = NULL; 1094 1148 self->children_txns = NULL; 1149 self->children_logcursors = NULL ; 1095 1150 Py_INCREF(Py_None); 1096 1151 self->private_obj = Py_None; … … 1164 1219 self->parent_txn = NULL; 1165 1220 self->env = NULL; 1221 /* We initialize just in case "txn_begin" fails */ 1222 self->txn = NULL; 1166 1223 1167 1224 if (parent && ((PyObject *)parent!=Py_None)) { … … 1177 1234 1178 1235 if (makeDBError(err)) { 1236 /* Free object half initialized */ 1179 1237 Py_DECREF(self); 1180 1238 return NULL; … … 1210 1268 int flag_prepare = self->flag_prepare; 1211 1269 1212 dummy=DBTxn_abort_discard_internal(self, 0);1270 dummy=DBTxn_abort_discard_internal(self, 0); 1213 1271 /* 1214 1272 ** Raising exceptions while doing … … 1233 1291 Py_DECREF(self->env); 1234 1292 } else { 1235 Py_DECREF(self->parent_txn); 1293 /* 1294 ** We can have "self->env==NULL" and "self->parent_txn==NULL" 1295 ** if something happens when creating the transaction object 1296 ** and we abort the object while half done. 1297 */ 1298 Py_XDECREF(self->parent_txn); 1236 1299 } 1237 1300 PyObject_Del(self); … … 1248 1311 return NULL; 1249 1312 self->in_weakreflist = NULL; 1313 self->lock_initialized = 0; /* Just in case the call fails */ 1250 1314 1251 1315 MYDB_BEGIN_ALLOW_THREADS; … … 1256 1320 Py_DECREF(self); 1257 1321 self = NULL; 1322 } else { 1323 self->lock_initialized = 1; 1258 1324 } 1259 1325 … … 1269 1335 } 1270 1336 /* TODO: is this lock held? should we release it? */ 1337 /* CAUTION: The lock can be not initialized if the creation has failed */ 1271 1338 1272 1339 PyObject_Del(self); … … 1289 1356 1290 1357 self->in_weakreflist = NULL; 1358 self->sequence = NULL; /* Just in case the call fails */ 1291 1359 1292 1360 MYDB_BEGIN_ALLOW_THREADS; … … 1407 1475 secKey->flags = DB_DBT_APPMALLOC; /* DB will free */ 1408 1476 secKey->data = malloc(size); /* TODO, check this */ 1409 1410 1411 1412 1413 1414 1415 1477 if (secKey->data) { 1478 memcpy(secKey->data, data, size); 1479 secKey->size = size; 1480 retval = 0; 1481 } 1482 else { 1483 PyErr_SetString(PyExc_MemoryError, 1416 1484 "malloc failed in _db_associateCallback"); 1417 1418 1485 PyErr_Print(); 1486 } 1419 1487 } 1488 #if (DBVER >= 46) 1489 else if (PyList_Check(result)) 1490 { 1491 char* data; 1492 Py_ssize_t size; 1493 int i, listlen; 1494 DBT* dbts; 1495 1496 listlen = PyList_Size(result); 1497 1498 dbts = (DBT *)malloc(sizeof(DBT) * listlen); 1499 1500 for (i=0; i<listlen; i++) 1501 { 1502 if (!PyBytes_Check(PyList_GetItem(result, i))) 1503 { 1504 PyErr_SetString( 1505 PyExc_TypeError, 1506 #if (PY_VERSION_HEX < 0x03000000) 1507 "The list returned by DB->associate callback should be a list of strings."); 1508 #else 1509 "The list returned by DB->associate callback should be a list of bytes."); 1510 #endif 1511 PyErr_Print(); 1512 } 1513 1514 PyBytes_AsStringAndSize( 1515 PyList_GetItem(result, i), 1516 &data, &size); 1517 1518 CLEAR_DBT(dbts[i]); 1519 dbts[i].data = malloc(size); /* TODO, check this */ 1520 1521 if (dbts[i].data) 1522 { 1523 memcpy(dbts[i].data, data, size); 1524 dbts[i].size = size; 1525 dbts[i].ulen = dbts[i].size; 1526 dbts[i].flags = DB_DBT_APPMALLOC; /* DB will free */ 1527 } 1528 else 1529 { 1530 PyErr_SetString(PyExc_MemoryError, 1531 "malloc failed in _db_associateCallback (list)"); 1532 PyErr_Print(); 1533 } 1534 } 1535 1536 CLEAR_DBT(*secKey); 1537 1538 secKey->data = dbts; 1539 secKey->size = listlen; 1540 secKey->flags = DB_DBT_APPMALLOC | DB_DBT_MULTIPLE; 1541 retval = 0; 1542 } 1543 #endif 1420 1544 else { 1421 1545 PyErr_SetString( 1422 1546 PyExc_TypeError, 1423 "DB associate callback should return DB_DONOTINDEX or string."); 1547 #if (PY_VERSION_HEX < 0x03000000) 1548 "DB associate callback should return DB_DONOTINDEX/string/list of strings."); 1549 #else 1550 "DB associate callback should return DB_DONOTINDEX/bytes/list of bytes."); 1551 #endif 1424 1552 PyErr_Print(); 1425 1553 } … … 1440 1568 DBObject* secondaryDB; 1441 1569 PyObject* callback; 1442 #if (DBVER >= 41)1443 1570 PyObject *txnobj = NULL; 1444 1571 DB_TXN *txn = NULL; 1445 1572 static char* kwnames[] = {"secondaryDB", "callback", "flags", "txn", 1446 1573 NULL}; 1447 #else 1448 static char* kwnames[] = {"secondaryDB", "callback", "flags", NULL}; 1449 #endif 1450 1451 #if (DBVER >= 41) 1574 1452 1575 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|iO:associate", kwnames, 1453 1576 &secondaryDB, &callback, &flags, 1454 1577 &txnobj)) { 1455 #else 1456 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|i:associate", kwnames, 1457 &secondaryDB, &callback, &flags)) { 1458 #endif 1459 return NULL; 1460 } 1461 1462 #if (DBVER >= 41) 1578 return NULL; 1579 } 1580 1463 1581 if (!checkTxnObj(txnobj, &txn)) return NULL; 1464 #endif1465 1582 1466 1583 CHECK_DB_NOT_CLOSED(self); … … 1498 1615 #endif 1499 1616 MYDB_BEGIN_ALLOW_THREADS; 1500 #if (DBVER >= 41)1501 1617 err = self->db->associate(self->db, 1502 1618 txn, 1503 1619 secondaryDB->db, 1504 1620 _db_associateCallback, 1505 1621 flags); 1506 #else1507 err = self->db->associate(self->db,1508 secondaryDB->db,1509 _db_associateCallback,1510 flags);1511 #endif1512 1622 MYDB_END_ALLOW_THREADS; 1513 1623 … … 1618 1728 1619 1729 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 1620 1730 && self->moduleFlags.getReturnsNone) { 1621 1731 err = 0; 1622 1732 Py_INCREF(Py_None); … … 1702 1812 1703 1813 1814 #if (DBVER >= 47) 1815 /* 1816 ** This function is available since Berkeley DB 4.4, 1817 ** but 4.6 version is so buggy that we only support 1818 ** it from BDB 4.7 and newer. 1819 */ 1820 static PyObject* 1821 DB_compact(DBObject* self, PyObject* args, PyObject* kwargs) 1822 { 1823 PyObject* txnobj = NULL; 1824 PyObject *startobj = NULL, *stopobj = NULL; 1825 int flags = 0; 1826 DB_TXN *txn = NULL; 1827 DBT *start_p = NULL, *stop_p = NULL; 1828 DBT start, stop; 1829 int err; 1830 DB_COMPACT c_data = { 0 }; 1831 static char* kwnames[] = { "txn", "start", "stop", "flags", 1832 "compact_fillpercent", "compact_pages", 1833 "compact_timeout", NULL }; 1834 1835 1836 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|OOOiiiI:compact", kwnames, 1837 &txnobj, &startobj, &stopobj, &flags, 1838 &c_data.compact_fillpercent, 1839 &c_data.compact_pages, 1840 &c_data.compact_timeout)) 1841 return NULL; 1842 1843 CHECK_DB_NOT_CLOSED(self); 1844 if (!checkTxnObj(txnobj, &txn)) { 1845 return NULL; 1846 } 1847 1848 if (startobj && make_key_dbt(self, startobj, &start, NULL)) { 1849 start_p = &start; 1850 } 1851 if (stopobj && make_key_dbt(self, stopobj, &stop, NULL)) { 1852 stop_p = &stop; 1853 } 1854 1855 MYDB_BEGIN_ALLOW_THREADS; 1856 err = self->db->compact(self->db, txn, start_p, stop_p, &c_data, 1857 flags, NULL); 1858 MYDB_END_ALLOW_THREADS; 1859 1860 if (startobj) 1861 FREE_DBT(start); 1862 if (stopobj) 1863 FREE_DBT(stop); 1864 1865 RETURN_IF_ERR(); 1866 1867 return PyLong_FromUnsignedLong(c_data.compact_pages_truncated); 1868 } 1869 #endif 1870 1871 1704 1872 static PyObject* 1705 1873 DB_fd(DBObject* self) … … 1716 1884 } 1717 1885 1886 1887 #if (DBVER >= 46) 1888 static PyObject* 1889 DB_exists(DBObject* self, PyObject* args, PyObject* kwargs) 1890 { 1891 int err, flags=0; 1892 PyObject* txnobj = NULL; 1893 PyObject* keyobj; 1894 DBT key; 1895 DB_TXN *txn; 1896 1897 static char* kwnames[] = {"key", "txn", "flags", NULL}; 1898 1899 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|Oi:exists", kwnames, 1900 &keyobj, &txnobj, &flags)) 1901 return NULL; 1902 1903 CHECK_DB_NOT_CLOSED(self); 1904 if (!make_key_dbt(self, keyobj, &key, NULL)) 1905 return NULL; 1906 if (!checkTxnObj(txnobj, &txn)) { 1907 FREE_DBT(key); 1908 return NULL; 1909 } 1910 1911 MYDB_BEGIN_ALLOW_THREADS; 1912 err = self->db->exists(self->db, txn, &key, flags); 1913 MYDB_END_ALLOW_THREADS; 1914 1915 FREE_DBT(key); 1916 1917 if (!err) { 1918 Py_INCREF(Py_True); 1919 return Py_True; 1920 } 1921 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY)) { 1922 Py_INCREF(Py_False); 1923 return Py_False; 1924 } 1925 1926 /* 1927 ** If we reach there, there was an error. The 1928 ** "return" should be unreachable. 1929 */ 1930 RETURN_IF_ERR(); 1931 assert(0); /* This coude SHOULD be unreachable */ 1932 return NULL; 1933 } 1934 #endif 1718 1935 1719 1936 static PyObject* … … 1765 1982 } 1766 1983 else if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 1767 1984 && self->moduleFlags.getReturnsNone) { 1768 1985 err = 0; 1769 1986 Py_INCREF(Py_None); … … 1834 2051 } 1835 2052 else if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 1836 2053 && self->moduleFlags.getReturnsNone) { 1837 2054 err = 0; 1838 2055 Py_INCREF(Py_None); … … 1969 2186 1970 2187 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 1971 2188 && self->moduleFlags.getReturnsNone) { 1972 2189 err = 0; 1973 2190 Py_INCREF(Py_None); … … 2043 2260 cursors = malloc((length+1) * sizeof(DBC*)); 2044 2261 if (!cursors) { 2045 2046 2262 PyErr_NoMemory(); 2263 return NULL; 2047 2264 } 2048 2265 … … 2115 2332 char* filename = NULL; 2116 2333 char* dbname = NULL; 2117 #if (DBVER >= 41)2118 2334 PyObject *txnobj = NULL; 2119 2335 DB_TXN *txn = NULL; … … 2124 2340 static char* kwnames_basic[] = { 2125 2341 "filename", "dbtype", "flags", "mode", "txn", NULL}; 2126 #else 2127 /* with dbname */ 2128 static char* kwnames[] = { 2129 "filename", "dbname", "dbtype", "flags", "mode", NULL}; 2130 /* without dbname */ 2131 static char* kwnames_basic[] = { 2132 "filename", "dbtype", "flags", "mode", NULL}; 2133 #endif 2134 2135 #if (DBVER >= 41) 2342 2136 2343 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "z|ziiiO:open", kwnames, 2137 2344 &filename, &dbname, &type, &flags, &mode, 2138 2345 &txnobj)) 2139 #else2140 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "z|ziii:open", kwnames,2141 &filename, &dbname, &type, &flags,2142 &mode))2143 #endif2144 2346 { 2145 PyErr_Clear(); 2146 type = DB_UNKNOWN; flags = 0; mode = 0660; 2147 filename = NULL; dbname = NULL; 2148 #if (DBVER >= 41) 2149 if (!PyArg_ParseTupleAndKeywords(args, kwargs,"z|iiiO:open", 2347 PyErr_Clear(); 2348 type = DB_UNKNOWN; flags = 0; mode = 0660; 2349 filename = NULL; dbname = NULL; 2350 if (!PyArg_ParseTupleAndKeywords(args, kwargs,"z|iiiO:open", 2150 2351 kwnames_basic, 2151 2352 &filename, &type, &flags, &mode, 2152 2353 &txnobj)) 2153 return NULL; 2154 #else 2155 if (!PyArg_ParseTupleAndKeywords(args, kwargs,"z|iii:open", 2156 kwnames_basic, 2157 &filename, &type, &flags, &mode)) 2158 return NULL; 2159 #endif 2160 } 2161 2162 #if (DBVER >= 41) 2354 return NULL; 2355 } 2356 2163 2357 if (!checkTxnObj(txnobj, &txn)) return NULL; 2164 #endif2165 2358 2166 2359 if (NULL == self->db) { … … 2174 2367 } 2175 2368 2176 #if (DBVER >= 41)2177 2369 if (txn) { /* Can't use 'txnobj' because could be 'txnobj==Py_None' */ 2178 2370 INSERT_IN_DOUBLE_LINKED_LIST_TXN(((DBTxnObject *)txnobj)->children_dbs,self); … … 2181 2373 self->txn=NULL; 2182 2374 } 2183 #else 2184 self->txn=NULL; 2185 #endif 2186 2187 MYDB_BEGIN_ALLOW_THREADS; 2188 #if (DBVER >= 41) 2375 2376 MYDB_BEGIN_ALLOW_THREADS; 2189 2377 err = self->db->open(self->db, txn, filename, dbname, type, flags, mode); 2190 #else 2191 err = self->db->open(self->db, filename, dbname, type, flags, mode); 2192 #endif 2193 MYDB_END_ALLOW_THREADS; 2378 MYDB_END_ALLOW_THREADS; 2379 2194 2380 if (makeDBError(err)) { 2195 2381 PyObject *dummy; … … 2320 2506 } 2321 2507 2508 #if (DBVER >= 46) 2509 static PyObject* 2510 DB_set_priority(DBObject* self, PyObject* args) 2511 { 2512 int err, priority; 2513 2514 if (!PyArg_ParseTuple(args,"i:set_priority", &priority)) 2515 return NULL; 2516 CHECK_DB_NOT_CLOSED(self); 2517 2518 MYDB_BEGIN_ALLOW_THREADS; 2519 err = self->db->set_priority(self->db, priority); 2520 MYDB_END_ALLOW_THREADS; 2521 RETURN_IF_ERR(); 2522 RETURN_NONE(); 2523 } 2524 2525 static PyObject* 2526 DB_get_priority(DBObject* self) 2527 { 2528 int err = 0; 2529 DB_CACHE_PRIORITY priority; 2530 2531 CHECK_DB_NOT_CLOSED(self); 2532 2533 MYDB_BEGIN_ALLOW_THREADS; 2534 err = self->db->get_priority(self->db, &priority); 2535 MYDB_END_ALLOW_THREADS; 2536 RETURN_IF_ERR(); 2537 return NUMBER_FromLong(priority); 2538 } 2539 #endif 2540 2541 static PyObject* 2542 DB_set_q_extentsize(DBObject* self, PyObject* args) 2543 { 2544 int err; 2545 u_int32_t extentsize; 2546 2547 if (!PyArg_ParseTuple(args,"i:set_q_extentsize", &extentsize)) 2548 return NULL; 2549 CHECK_DB_NOT_CLOSED(self); 2550 2551 MYDB_BEGIN_ALLOW_THREADS; 2552 err = self->db->set_q_extentsize(self->db, extentsize); 2553 MYDB_END_ALLOW_THREADS; 2554 RETURN_IF_ERR(); 2555 RETURN_NONE(); 2556 } 2557 2558 #if (DBVER >= 42) 2559 static PyObject* 2560 DB_get_q_extentsize(DBObject* self) 2561 { 2562 int err = 0; 2563 u_int32_t extentsize; 2564 2565 CHECK_DB_NOT_CLOSED(self); 2566 2567 MYDB_BEGIN_ALLOW_THREADS; 2568 err = self->db->get_q_extentsize(self->db, &extentsize); 2569 MYDB_END_ALLOW_THREADS; 2570 RETURN_IF_ERR(); 2571 return NUMBER_FromLong(extentsize); 2572 } 2573 #endif 2322 2574 2323 2575 static PyObject* … … 2326 2578 int err, minkey; 2327 2579 2328 if (!PyArg_ParseTuple(args,"i:set_bt_minkey", &minkey 2580 if (!PyArg_ParseTuple(args,"i:set_bt_minkey", &minkey)) 2329 2581 return NULL; 2330 2582 CHECK_DB_NOT_CLOSED(self); … … 2336 2588 RETURN_NONE(); 2337 2589 } 2590 2591 #if (DBVER >= 42) 2592 static PyObject* 2593 DB_get_bt_minkey(DBObject* self) 2594 { 2595 int err; 2596 u_int32_t bt_minkey; 2597 2598 CHECK_DB_NOT_CLOSED(self); 2599 2600 MYDB_BEGIN_ALLOW_THREADS; 2601 err = self->db->get_bt_minkey(self->db, &bt_minkey); 2602 MYDB_END_ALLOW_THREADS; 2603 RETURN_IF_ERR(); 2604 return NUMBER_FromLong(bt_minkey); 2605 } 2606 #endif 2338 2607 2339 2608 static int 2340 2609 _default_cmp(const DBT *leftKey, 2341 2610 const DBT *rightKey) 2342 2611 { 2343 2612 int res; … … 2345 2614 2346 2615 res = memcmp(leftKey->data, rightKey->data, 2347 2616 lsize < rsize ? lsize : rsize); 2348 2617 2349 2618 if (res == 0) { 2350 2619 if (lsize < rsize) { 2351 2620 res = -1; 2352 2621 } 2353 2622 else if (lsize > rsize) { 2354 2623 res = 1; 2355 2624 } 2356 2625 } … … 2360 2629 static int 2361 2630 _db_compareCallback(DB* db, 2362 2363 2631 const DBT *leftKey, 2632 const DBT *rightKey) 2364 2633 { 2365 2634 int res = 0; … … 2369 2638 2370 2639 if (self == NULL || self->btCompareCallback == NULL) { 2371 2372 2373 2374 2375 2376 2377 2378 2379 2640 MYDB_BEGIN_BLOCK_THREADS; 2641 PyErr_SetString(PyExc_TypeError, 2642 (self == 0 2643 ? "DB_bt_compare db is NULL." 2644 : "DB_bt_compare callback is NULL.")); 2645 /* we're in a callback within the DB code, we can't raise */ 2646 PyErr_Print(); 2647 res = _default_cmp(leftKey, rightKey); 2648 MYDB_END_BLOCK_THREADS; 2380 2649 } else { 2381 2382 2383 2384 2385 2386 2387 2388 2389 2390 2391 2392 2393 2394 2395 2396 2397 2398 2399 2400 2401 2402 2403 2404 2650 MYDB_BEGIN_BLOCK_THREADS; 2651 2652 args = BuildValue_SS(leftKey->data, leftKey->size, rightKey->data, rightKey->size); 2653 if (args != NULL) { 2654 result = PyEval_CallObject(self->btCompareCallback, args); 2655 } 2656 if (args == NULL || result == NULL) { 2657 /* we're in a callback within the DB code, we can't raise */ 2658 PyErr_Print(); 2659 res = _default_cmp(leftKey, rightKey); 2660 } else if (NUMBER_Check(result)) { 2661 res = NUMBER_AsLong(result); 2662 } else { 2663 PyErr_SetString(PyExc_TypeError, 2664 "DB_bt_compare callback MUST return an int."); 2665 /* we're in a callback within the DB code, we can't raise */ 2666 PyErr_Print(); 2667 res = _default_cmp(leftKey, rightKey); 2668 } 2669 2670 Py_XDECREF(args); 2671 Py_XDECREF(result); 2672 2673 MYDB_END_BLOCK_THREADS; 2405 2674 } 2406 2675 return res; … … 2416 2685 2417 2686 if (!PyCallable_Check(comparator)) { 2418 2419 2687 makeTypeError("Callable", comparator); 2688 return NULL; 2420 2689 } 2421 2690 … … 2431 2700 return NULL; 2432 2701 if (!NUMBER_Check(result)) { 2433 2434 2435 2436 2702 Py_DECREF(result); 2703 PyErr_SetString(PyExc_TypeError, 2704 "callback MUST return an int"); 2705 return NULL; 2437 2706 } else if (NUMBER_AsLong(result) != 0) { 2438 2439 2440 2441 2707 Py_DECREF(result); 2708 PyErr_SetString(PyExc_TypeError, 2709 "callback failed to return 0 on two empty strings"); 2710 return NULL; 2442 2711 } 2443 2712 Py_DECREF(result); … … 2447 2716 * change the function once the db is opened anyway */ 2448 2717 if (self->btCompareCallback != NULL) { 2449 2450 2718 PyErr_SetString(PyExc_RuntimeError, "set_bt_compare() cannot be called more than once"); 2719 return NULL; 2451 2720 } 2452 2721 … … 2463 2732 2464 2733 if (err) { 2465 2466 2467 2734 /* restore the old state in case of error */ 2735 Py_DECREF(comparator); 2736 self->btCompareCallback = NULL; 2468 2737 } 2469 2738 … … 2491 2760 } 2492 2761 2762 #if (DBVER >= 42) 2763 static PyObject* 2764 DB_get_cachesize(DBObject* self) 2765 { 2766 int err; 2767 u_int32_t gbytes, bytes; 2768 int ncache; 2769 2770 CHECK_DB_NOT_CLOSED(self); 2771 2772 MYDB_BEGIN_ALLOW_THREADS; 2773 err = self->db->get_cachesize(self->db, &gbytes, &bytes, &ncache); 2774 MYDB_END_ALLOW_THREADS; 2775 2776 RETURN_IF_ERR(); 2777 2778 return Py_BuildValue("(iii)", gbytes, bytes, ncache); 2779 } 2780 #endif 2493 2781 2494 2782 static PyObject* … … 2510 2798 } 2511 2799 2800 #if (DBVER >= 42) 2801 static PyObject* 2802 DB_get_flags(DBObject* self) 2803 { 2804 int err; 2805 u_int32_t flags; 2806 2807 CHECK_DB_NOT_CLOSED(self); 2808 2809 MYDB_BEGIN_ALLOW_THREADS; 2810 err = self->db->get_flags(self->db, &flags); 2811 MYDB_END_ALLOW_THREADS; 2812 RETURN_IF_ERR(); 2813 return NUMBER_FromLong(flags); 2814 } 2815 #endif 2512 2816 2513 2817 static PyObject* … … 2527 2831 } 2528 2832 2833 #if (DBVER >= 42) 2834 static PyObject* 2835 DB_get_h_ffactor(DBObject* self) 2836 { 2837 int err; 2838 u_int32_t ffactor; 2839 2840 CHECK_DB_NOT_CLOSED(self); 2841 2842 MYDB_BEGIN_ALLOW_THREADS; 2843 err = self->db->get_h_ffactor(self->db, &ffactor); 2844 MYDB_END_ALLOW_THREADS; 2845 RETURN_IF_ERR(); 2846 return NUMBER_FromLong(ffactor); 2847 } 2848 #endif 2529 2849 2530 2850 static PyObject* … … 2544 2864 } 2545 2865 2866 #if (DBVER >= 42) 2867 static PyObject* 2868 DB_get_h_nelem(DBObject* self) 2869 { 2870 int err; 2871 u_int32_t nelem; 2872 2873 CHECK_DB_NOT_CLOSED(self); 2874 2875 MYDB_BEGIN_ALLOW_THREADS; 2876 err = self->db->get_h_nelem(self->db, &nelem); 2877 MYDB_END_ALLOW_THREADS; 2878 RETURN_IF_ERR(); 2879 return NUMBER_FromLong(nelem); 2880 } 2881 #endif 2546 2882 2547 2883 static PyObject* … … 2561 2897 } 2562 2898 2899 #if (DBVER >= 42) 2900 static PyObject* 2901 DB_get_lorder(DBObject* self) 2902 { 2903 int err; 2904 int lorder; 2905 2906 CHECK_DB_NOT_CLOSED(self); 2907 2908 MYDB_BEGIN_ALLOW_THREADS; 2909 err = self->db->get_lorder(self->db, &lorder); 2910 MYDB_END_ALLOW_THREADS; 2911 RETURN_IF_ERR(); 2912 return NUMBER_FromLong(lorder); 2913 } 2914 #endif 2563 2915 2564 2916 static PyObject* … … 2578 2930 } 2579 2931 2932 #if (DBVER >= 42) 2933 static PyObject* 2934 DB_get_pagesize(DBObject* self) 2935 { 2936 int err; 2937 u_int32_t pagesize; 2938 2939 CHECK_DB_NOT_CLOSED(self); 2940 2941 MYDB_BEGIN_ALLOW_THREADS; 2942 err = self->db->get_pagesize(self->db, &pagesize); 2943 MYDB_END_ALLOW_THREADS; 2944 RETURN_IF_ERR(); 2945 return NUMBER_FromLong(pagesize); 2946 } 2947 #endif 2580 2948 2581 2949 static PyObject* … … 2600 2968 } 2601 2969 2970 #if (DBVER >= 42) 2971 static PyObject* 2972 DB_get_re_delim(DBObject* self) 2973 { 2974 int err, re_delim; 2975 2976 CHECK_DB_NOT_CLOSED(self); 2977 2978 MYDB_BEGIN_ALLOW_THREADS; 2979 err = self->db->get_re_delim(self->db, &re_delim); 2980 MYDB_END_ALLOW_THREADS; 2981 RETURN_IF_ERR(); 2982 return NUMBER_FromLong(re_delim); 2983 } 2984 #endif 2985 2602 2986 static PyObject* 2603 2987 DB_set_re_len(DBObject* self, PyObject* args) … … 2616 3000 } 2617 3001 3002 #if (DBVER >= 42) 3003 static PyObject* 3004 DB_get_re_len(DBObject* self) 3005 { 3006 int err; 3007 u_int32_t re_len; 3008 3009 CHECK_DB_NOT_CLOSED(self); 3010 3011 MYDB_BEGIN_ALLOW_THREADS; 3012 err = self->db->get_re_len(self->db, &re_len); 3013 MYDB_END_ALLOW_THREADS; 3014 RETURN_IF_ERR(); 3015 return NUMBER_FromLong(re_len); 3016 } 3017 #endif 2618 3018 2619 3019 static PyObject* … … 2637 3037 } 2638 3038 3039 #if (DBVER >= 42) 3040 static PyObject* 3041 DB_get_re_pad(DBObject* self) 3042 { 3043 int err, re_pad; 3044 3045 CHECK_DB_NOT_CLOSED(self); 3046 3047 MYDB_BEGIN_ALLOW_THREADS; 3048 err = self->db->get_re_pad(self->db, &re_pad); 3049 MYDB_END_ALLOW_THREADS; 3050 RETURN_IF_ERR(); 3051 return NUMBER_FromLong(re_pad); 3052 } 3053 #endif 2639 3054 2640 3055 static PyObject* … … 2642 3057 { 2643 3058 int err; 2644 char * re_source;2645 2646 if (!PyArg_ParseTuple(args,"s:set_re_source", & re_source))3059 char *source; 3060 3061 if (!PyArg_ParseTuple(args,"s:set_re_source", &source)) 2647 3062 return NULL; 2648 3063 CHECK_DB_NOT_CLOSED(self); 2649 3064 2650 3065 MYDB_BEGIN_ALLOW_THREADS; 2651 err = self->db->set_re_source(self->db, re_source); 2652 MYDB_END_ALLOW_THREADS; 2653 RETURN_IF_ERR(); 2654 RETURN_NONE(); 2655 } 2656 2657 2658 static PyObject* 2659 DB_set_q_extentsize(DBObject* self, PyObject* args) 2660 { 2661 int err; 2662 int extentsize; 2663 2664 if (!PyArg_ParseTuple(args,"i:set_q_extentsize", &extentsize)) 2665 return NULL; 3066 err = self->db->set_re_source(self->db, source); 3067 MYDB_END_ALLOW_THREADS; 3068 RETURN_IF_ERR(); 3069 RETURN_NONE(); 3070 } 3071 3072 #if (DBVER >= 42) 3073 static PyObject* 3074 DB_get_re_source(DBObject* self) 3075 { 3076 int err; 3077 const char *source; 3078 2666 3079 CHECK_DB_NOT_CLOSED(self); 2667 3080 2668 3081 MYDB_BEGIN_ALLOW_THREADS; 2669 err = self->db->set_q_extentsize(self->db, extentsize); 2670 MYDB_END_ALLOW_THREADS; 2671 RETURN_IF_ERR(); 2672 RETURN_NONE(); 2673 } 3082 err = self->db->get_re_source(self->db, &source); 3083 MYDB_END_ALLOW_THREADS; 3084 RETURN_IF_ERR(); 3085 return PyBytes_FromString(source); 3086 } 3087 #endif 2674 3088 2675 3089 static PyObject* … … 2708 3122 RETURN_IF_ERR(); 2709 3123 2710 self->haveStat = 1;2711 2712 3124 /* Turn the stat structure into a dictionary */ 2713 3125 type = _DB_get_type(self); … … 2731 3143 #endif 2732 3144 MAKE_HASH_ENTRY(pagesize); 2733 #if (DBVER < 41)2734 MAKE_HASH_ENTRY(nelem);2735 #endif2736 3145 MAKE_HASH_ENTRY(ffactor); 2737 3146 MAKE_HASH_ENTRY(buckets); … … 2780 3189 MAKE_QUEUE_ENTRY(ndata); 2781 3190 MAKE_QUEUE_ENTRY(pagesize); 2782 #if (DBVER >= 41)2783 3191 MAKE_QUEUE_ENTRY(extentsize); 2784 #endif2785 3192 MAKE_QUEUE_ENTRY(pages); 2786 3193 MAKE_QUEUE_ENTRY(re_len); … … 2807 3214 return d; 2808 3215 } 3216 3217 #if (DBVER >= 43) 3218 static PyObject* 3219 DB_stat_print(DBObject* self, PyObject* args, PyObject *kwargs) 3220 { 3221 int err; 3222 int flags=0; 3223 static char* kwnames[] = { "flags", NULL }; 3224 3225 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:stat_print", 3226 kwnames, &flags)) 3227 { 3228 return NULL; 3229 } 3230 CHECK_DB_NOT_CLOSED(self); 3231 MYDB_BEGIN_ALLOW_THREADS; 3232 err = self->db->stat_print(self->db, flags); 3233 MYDB_END_ALLOW_THREADS; 3234 RETURN_IF_ERR(); 3235 RETURN_NONE(); 3236 } 3237 #endif 3238 2809 3239 2810 3240 static PyObject* … … 2886 3316 if (outFileName) 2887 3317 outFile = fopen(outFileName, "w"); 2888 2889 3318 /* XXX(nnorwitz): it should probably be an exception if outFile 3319 can't be opened. */ 2890 3320 2891 3321 { /* DB.verify acts as a DB handle destructor (like close) */ … … 2893 3323 2894 3324 error=DB_close_internal(self, 0, 1); 2895 if (error 3325 if (error) { 2896 3326 return error; 2897 3327 } … … 2931 3361 } 2932 3362 2933 #if (DBVER >= 41)2934 3363 static PyObject* 2935 3364 DB_set_encrypt(DBObject* self, PyObject* args, PyObject* kwargs) … … 2941 3370 2942 3371 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s|i:set_encrypt", kwnames, 2943 2944 3372 &passwd, &flags)) { 3373 return NULL; 2945 3374 } 2946 3375 … … 2952 3381 RETURN_NONE(); 2953 3382 } 2954 #endif /* DBVER >= 41 */ 3383 3384 #if (DBVER >= 42) 3385 static PyObject* 3386 DB_get_encrypt_flags(DBObject* self) 3387 { 3388 int err; 3389 u_int32_t flags; 3390 3391 MYDB_BEGIN_ALLOW_THREADS; 3392 err = self->db->get_encrypt_flags(self->db, &flags); 3393 MYDB_END_ALLOW_THREADS; 3394 3395 RETURN_IF_ERR(); 3396 3397 return NUMBER_FromLong(flags); 3398 } 3399 #endif 3400 2955 3401 2956 3402 … … 2962 3408 int err; 2963 3409 Py_ssize_t size = 0; 2964 int flags = 0;2965 3410 void* sp; 2966 3411 DBObject* self = (DBObject*)_self; … … 2975 3420 } 2976 3421 2977 if (self->haveStat) { /* Has the stat function been called recently? If 2978 so, we can use the cached value. */ 2979 flags = DB_FAST_STAT; 2980 } 2981 2982 MYDB_BEGIN_ALLOW_THREADS; 2983 redo_stat_for_length: 3422 MYDB_BEGIN_ALLOW_THREADS; 2984 3423 #if (DBVER >= 43) 2985 err = self->db->stat(self->db, /*txnid*/ NULL, &sp, flags);3424 err = self->db->stat(self->db, /*txnid*/ NULL, &sp, 0); 2986 3425 #else 2987 err = self->db->stat(self->db, &sp, flags); 2988 #endif 3426 err = self->db->stat(self->db, &sp, 0); 3427 #endif 3428 MYDB_END_ALLOW_THREADS; 2989 3429 2990 3430 /* All the stat structures have matching fields upto the ndata field, … … 2992 3432 size = ((DB_BTREE_STAT*)sp)->bt_ndata; 2993 3433 2994 /* A size of 0 could mean that Berkeley DB no longer had the stat values cached.2995 * redo a full stat to make sure.2996 * Fixes SF python bug 1493322, pybsddb bug 11840122997 */2998 if (size == 0 && (flags & DB_FAST_STAT)) {2999 flags = 0;3000 if (!err)3001 free(sp);3002 goto redo_stat_for_length;3003 }3004 3005 MYDB_END_ALLOW_THREADS;3006 3007 3434 if (err) 3008 3435 return -1; 3009 3010 self->haveStat = 1;3011 3436 3012 3437 free(sp); … … 3098 3523 3099 3524 static PyObject* 3100 DB_has_key(DBObject* self, PyObject* args, PyObject* kwargs) 3101 { 3102 int err; 3103 PyObject* keyobj; 3104 DBT key, data; 3105 PyObject* txnobj = NULL; 3525 _DB_has_key(DBObject* self, PyObject* keyobj, PyObject* txnobj) 3526 { 3527 int err; 3528 DBT key; 3106 3529 DB_TXN *txn = NULL; 3107 static char* kwnames[] = {"key","txn", NULL};3108 3109 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|O:has_key", kwnames,3110 &keyobj, &txnobj))3111 return NULL;3112 3530 3113 3531 CHECK_DB_NOT_CLOSED(self); … … 3119 3537 } 3120 3538 3539 #if (DBVER < 46) 3121 3540 /* This causes DB_BUFFER_SMALL to be returned when the db has the key because 3122 3541 it has a record but can't allocate a buffer for the data. This saves 3123 3542 having to deal with data we won't be using. 3124 3543 */ 3125 CLEAR_DBT(data); 3126 data.flags = DB_DBT_USERMEM; 3127 3128 MYDB_BEGIN_ALLOW_THREADS; 3129 err = self->db->get(self->db, txn, &key, &data, 0); 3130 MYDB_END_ALLOW_THREADS; 3544 { 3545 DBT data ; 3546 CLEAR_DBT(data); 3547 data.flags = DB_DBT_USERMEM; 3548 3549 MYDB_BEGIN_ALLOW_THREADS; 3550 err = self->db->get(self->db, txn, &key, &data, 0); 3551 MYDB_END_ALLOW_THREADS; 3552 } 3553 #else 3554 MYDB_BEGIN_ALLOW_THREADS; 3555 err = self->db->exists(self->db, txn, &key, 0); 3556 MYDB_END_ALLOW_THREADS; 3557 #endif 3558 3131 3559 FREE_DBT(key); 3132 3560 3561 /* 3562 ** DB_BUFFER_SMALL is only used if we use "get". 3563 ** We can drop it when we only use "exists", 3564 ** when we drop suport for Berkeley DB < 4.6. 3565 */ 3133 3566 if (err == DB_BUFFER_SMALL || err == 0) { 3134 return NUMBER_FromLong(1); 3567 Py_INCREF(Py_True); 3568 return Py_True; 3135 3569 } else if (err == DB_NOTFOUND || err == DB_KEYEMPTY) { 3136 return NUMBER_FromLong(0); 3570 Py_INCREF(Py_False); 3571 return Py_False; 3137 3572 } 3138 3573 3139 3574 makeDBError(err); 3140 3575 return NULL; 3576 } 3577 3578 static PyObject* 3579 DB_has_key(DBObject* self, PyObject* args, PyObject* kwargs) 3580 { 3581 PyObject* keyobj; 3582 PyObject* txnobj = NULL; 3583 static char* kwnames[] = {"key","txn", NULL}; 3584 3585 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|O:has_key", kwnames, 3586 &keyobj, &txnobj)) 3587 return NULL; 3588 3589 return _DB_has_key(self, keyobj, txnobj); 3590 } 3591 3592 3593 static int DB_contains(DBObject* self, PyObject* keyobj) 3594 { 3595 PyObject* result; 3596 int result2 = 0; 3597 3598 result = _DB_has_key(self, keyobj, NULL) ; 3599 if (result == NULL) { 3600 return -1; /* Propague exception */ 3601 } 3602 if (result != Py_False) { 3603 result2 = 1; 3604 } 3605 3606 Py_DECREF(result); 3607 return result2; 3141 3608 } 3142 3609 … … 3294 3761 3295 3762 /* --------------------------------------------------------------------- */ 3763 /* DBLogCursor methods */ 3764 3765 3766 static PyObject* 3767 DBLogCursor_close_internal(DBLogCursorObject* self) 3768 { 3769 int err = 0; 3770 3771 if (self->logc != NULL) { 3772 EXTRACT_FROM_DOUBLE_LINKED_LIST(self); 3773 3774 MYDB_BEGIN_ALLOW_THREADS; 3775 err = self->logc->close(self->logc, 0); 3776 MYDB_END_ALLOW_THREADS; 3777 self->logc = NULL; 3778 } 3779 RETURN_IF_ERR(); 3780 RETURN_NONE(); 3781 } 3782 3783 static PyObject* 3784 DBLogCursor_close(DBLogCursorObject* self) 3785 { 3786 return DBLogCursor_close_internal(self); 3787 } 3788 3789 3790 static PyObject* 3791 _DBLogCursor_get(DBLogCursorObject* self, int flag, DB_LSN *lsn2) 3792 { 3793 int err; 3794 DBT data; 3795 DB_LSN lsn = {0, 0}; 3796 PyObject *dummy, *retval; 3797 3798 CLEAR_DBT(data); 3799 data.flags = DB_DBT_MALLOC; /* Berkeley DB must do the malloc */ 3800 3801 CHECK_LOGCURSOR_NOT_CLOSED(self); 3802 3803 if (lsn2) 3804 lsn = *lsn2; 3805 3806 MYDB_BEGIN_ALLOW_THREADS; 3807 err = self->logc->get(self->logc, &lsn, &data, flag); 3808 MYDB_END_ALLOW_THREADS; 3809 3810 if (err == DB_NOTFOUND) { 3811 Py_INCREF(Py_None); 3812 retval = Py_None; 3813 } 3814 else if (makeDBError(err)) { 3815 retval = NULL; 3816 } 3817 else { 3818 retval = dummy = BuildValue_S(data.data, data.size); 3819 if (dummy) { 3820 retval = Py_BuildValue("(ii)O", lsn.file, lsn.offset, dummy); 3821 Py_DECREF(dummy); 3822 } 3823 } 3824 3825 FREE_DBT(data); 3826 return retval; 3827 } 3828 3829 static PyObject* 3830 DBLogCursor_current(DBLogCursorObject* self) 3831 { 3832 return _DBLogCursor_get(self, DB_CURRENT, NULL); 3833 } 3834 3835 static PyObject* 3836 DBLogCursor_first(DBLogCursorObject* self) 3837 { 3838 return _DBLogCursor_get(self, DB_FIRST, NULL); 3839 } 3840 3841 static PyObject* 3842 DBLogCursor_last(DBLogCursorObject* self) 3843 { 3844 return _DBLogCursor_get(self, DB_LAST, NULL); 3845 } 3846 3847 static PyObject* 3848 DBLogCursor_next(DBLogCursorObject* self) 3849 { 3850 return _DBLogCursor_get(self, DB_NEXT, NULL); 3851 } 3852 3853 static PyObject* 3854 DBLogCursor_prev(DBLogCursorObject* self) 3855 { 3856 return _DBLogCursor_get(self, DB_PREV, NULL); 3857 } 3858 3859 static PyObject* 3860 DBLogCursor_set(DBLogCursorObject* self, PyObject* args) 3861 { 3862 DB_LSN lsn; 3863 3864 if (!PyArg_ParseTuple(args, "(ii):set", &lsn.file, &lsn.offset)) 3865 return NULL; 3866 3867 return _DBLogCursor_get(self, DB_SET, &lsn); 3868 } 3869 3870 3871 3872 /* --------------------------------------------------------------------- */ 3296 3873 /* DBCursor methods */ 3297 3874 … … 3368 3945 RETURN_IF_ERR(); 3369 3946 3370 self->mydb->haveStat = 0;3371 3947 RETURN_NONE(); 3372 3948 } … … 3415 3991 CLEAR_DBT(data); 3416 3992 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i|ii:get", &kwnames[2], 3417 3993 &flags, &dlen, &doff)) 3418 3994 { 3419 3995 PyErr_Clear(); 3420 3996 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "Oi|ii:get", 3421 3997 &kwnames[1], 3422 3998 &keyobj, &flags, &dlen, &doff)) 3423 3999 { 3424 4000 PyErr_Clear(); … … 3428 4004 { 3429 4005 return NULL; 3430 3431 4006 } 4007 } 3432 4008 } 3433 4009 … … 3448 4024 3449 4025 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 3450 4026 && self->mydb->moduleFlags.getReturnsNone) { 3451 4027 Py_INCREF(Py_None); 3452 4028 retval = Py_None; … … 3491 4067 CLEAR_DBT(data); 3492 4068 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i|ii:pget", &kwnames[2], 3493 4069 &flags, &dlen, &doff)) 3494 4070 { 3495 4071 PyErr_Clear(); 3496 4072 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "Oi|ii:pget", 3497 kwnames_keyOnly, 3498 4073 kwnames_keyOnly, 4074 &keyobj, &flags, &dlen, &doff)) 3499 4075 { 3500 4076 PyErr_Clear(); … … 3504 4080 { 3505 4081 return NULL; 3506 3507 4082 } 4083 } 3508 4084 } 3509 4085 … … 3526 4102 3527 4103 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 3528 4104 && self->mydb->moduleFlags.getReturnsNone) { 3529 4105 Py_INCREF(Py_None); 3530 4106 retval = Py_None; … … 3637 4213 3638 4214 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OO|iii:put", kwnames, 3639 4215 &keyobj, &dataobj, &flags, &dlen, &doff)) 3640 4216 return NULL; 3641 4217 … … 3656 4232 FREE_DBT(key); /* 'make_key_dbt' could do a 'malloc' */ 3657 4233 RETURN_IF_ERR(); 3658 self->mydb->haveStat = 0;3659 4234 RETURN_NONE(); 3660 4235 } … … 3672 4247 3673 4248 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|iii:set", kwnames, 3674 4249 &keyobj, &flags, &dlen, &doff)) 3675 4250 return NULL; 3676 4251 … … 3690 4265 MYDB_END_ALLOW_THREADS; 3691 4266 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 3692 4267 && self->mydb->moduleFlags.cursorSetReturnsNone) { 3693 4268 Py_INCREF(Py_None); 3694 4269 retval = Py_None; … … 3735 4310 3736 4311 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O|iii:set_range", kwnames, 3737 4312 &keyobj, &flags, &dlen, &doff)) 3738 4313 return NULL; 3739 4314 … … 3752 4327 MYDB_END_ALLOW_THREADS; 3753 4328 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 3754 4329 && self->mydb->moduleFlags.cursorSetReturnsNone) { 3755 4330 Py_INCREF(Py_None); 3756 4331 retval = Py_None; … … 3906 4481 3907 4482 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i|iii:set_recno", kwnames, 3908 4483 &irecno, &flags, &dlen, &doff)) 3909 4484 return NULL; 3910 4485 … … 3935 4510 MYDB_END_ALLOW_THREADS; 3936 4511 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 3937 4512 && self->mydb->moduleFlags.cursorSetReturnsNone) { 3938 4513 Py_INCREF(Py_None); 3939 4514 retval = Py_None; … … 3971 4546 } 3972 4547 4548 #if (DBVER >= 46) 4549 static PyObject* 4550 DBC_prev_dup(DBCursorObject* self, PyObject* args, PyObject *kwargs) 4551 { 4552 return _DBCursor_get(self,DB_PREV_DUP,args,kwargs,"|iii:prev_dup"); 4553 } 4554 #endif 3973 4555 3974 4556 static PyObject* … … 3998 4580 MYDB_END_ALLOW_THREADS; 3999 4581 if ((err == DB_NOTFOUND || err == DB_KEYEMPTY) 4000 4582 && self->mydb->moduleFlags.getReturnsNone) { 4001 4583 Py_INCREF(Py_None); 4002 4584 retval = Py_None; … … 4013 4595 4014 4596 4597 #if (DBVER >= 46) 4598 static PyObject* 4599 DBC_set_priority(DBCursorObject* self, PyObject* args, PyObject* kwargs) 4600 { 4601 int err, priority; 4602 static char* kwnames[] = { "priority", NULL }; 4603 4604 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i:set_priority", kwnames, 4605 &priority)) 4606 return NULL; 4607 4608 CHECK_CURSOR_NOT_CLOSED(self); 4609 4610 MYDB_BEGIN_ALLOW_THREADS; 4611 err = self->dbc->set_priority(self->dbc, priority); 4612 MYDB_END_ALLOW_THREADS; 4613 RETURN_IF_ERR(); 4614 RETURN_NONE(); 4615 } 4616 4617 4618 static PyObject* 4619 DBC_get_priority(DBCursorObject* self) 4620 { 4621 int err; 4622 DB_CACHE_PRIORITY priority; 4623 4624 CHECK_CURSOR_NOT_CLOSED(self); 4625 4626 MYDB_BEGIN_ALLOW_THREADS; 4627 err = self->dbc->get_priority(self->dbc, &priority); 4628 MYDB_END_ALLOW_THREADS; 4629 RETURN_IF_ERR(); 4630 return NUMBER_FromLong(priority); 4631 } 4632 #endif 4633 4634 4015 4635 4016 4636 /* --------------------------------------------------------------------- */ … … 4026 4646 if (!self->closed) { /* Don't close more than once */ 4027 4647 while(self->children_txns) { 4028 dummy=DBTxn_abort_discard_internal(self->children_txns,0);4029 Py_XDECREF(dummy);4648 dummy = DBTxn_abort_discard_internal(self->children_txns, 0); 4649 Py_XDECREF(dummy); 4030 4650 } 4031 4651 while(self->children_dbs) { 4032 dummy=DB_close_internal(self->children_dbs, 0, 0); 4033 Py_XDECREF(dummy); 4652 dummy = DB_close_internal(self->children_dbs, 0, 0); 4653 Py_XDECREF(dummy); 4654 } 4655 while(self->children_logcursors) { 4656 dummy = DBLogCursor_close_internal(self->children_logcursors); 4657 Py_XDECREF(dummy); 4034 4658 } 4035 4659 } … … 4081 4705 4082 4706 static PyObject* 4707 DBEnv_memp_stat(DBEnvObject* self, PyObject* args, PyObject *kwargs) 4708 { 4709 int err; 4710 DB_MPOOL_STAT *gsp; 4711 DB_MPOOL_FSTAT **fsp, **fsp2; 4712 PyObject* d = NULL, *d2, *d3, *r; 4713 u_int32_t flags = 0; 4714 static char* kwnames[] = { "flags", NULL }; 4715 4716 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:memp_stat", 4717 kwnames, &flags)) 4718 return NULL; 4719 4720 CHECK_ENV_NOT_CLOSED(self); 4721 4722 MYDB_BEGIN_ALLOW_THREADS; 4723 err = self->db_env->memp_stat(self->db_env, &gsp, &fsp, flags); 4724 MYDB_END_ALLOW_THREADS; 4725 RETURN_IF_ERR(); 4726 4727 /* Turn the stat structure into a dictionary */ 4728 d = PyDict_New(); 4729 if (d == NULL) { 4730 if (gsp) 4731 free(gsp); 4732 return NULL; 4733 } 4734 4735 #define MAKE_ENTRY(name) _addIntToDict(d, #name, gsp->st_##name) 4736 4737 MAKE_ENTRY(gbytes); 4738 MAKE_ENTRY(ncache); 4739 #if (DBVER >= 46) 4740 MAKE_ENTRY(max_ncache); 4741 #endif 4742 MAKE_ENTRY(regsize); 4743 #if (DBVER >= 43) 4744 MAKE_ENTRY(mmapsize); 4745 MAKE_ENTRY(maxopenfd); 4746 MAKE_ENTRY(maxwrite); 4747 MAKE_ENTRY(maxwrite_sleep); 4748 #endif 4749 MAKE_ENTRY(map); 4750 MAKE_ENTRY(cache_hit); 4751 MAKE_ENTRY(cache_miss); 4752 MAKE_ENTRY(page_create); 4753 MAKE_ENTRY(page_in); 4754 MAKE_ENTRY(page_out); 4755 MAKE_ENTRY(ro_evict); 4756 MAKE_ENTRY(rw_evict); 4757 MAKE_ENTRY(page_trickle); 4758 MAKE_ENTRY(pages); 4759 MAKE_ENTRY(page_clean); 4760 MAKE_ENTRY(page_dirty); 4761 MAKE_ENTRY(hash_buckets); 4762 MAKE_ENTRY(hash_searches); 4763 MAKE_ENTRY(hash_longest); 4764 MAKE_ENTRY(hash_examined); 4765 MAKE_ENTRY(hash_nowait); 4766 MAKE_ENTRY(hash_wait); 4767 #if (DBVER >= 45) 4768 MAKE_ENTRY(hash_max_nowait); 4769 #endif 4770 MAKE_ENTRY(hash_max_wait); 4771 MAKE_ENTRY(region_wait); 4772 MAKE_ENTRY(region_nowait); 4773 #if (DBVER >= 45) 4774 MAKE_ENTRY(mvcc_frozen); 4775 MAKE_ENTRY(mvcc_thawed); 4776 MAKE_ENTRY(mvcc_freed); 4777 #endif 4778 MAKE_ENTRY(alloc); 4779 MAKE_ENTRY(alloc_buckets); 4780 MAKE_ENTRY(alloc_max_buckets); 4781 MAKE_ENTRY(alloc_pages); 4782 MAKE_ENTRY(alloc_max_pages); 4783 #if (DBVER >= 45) 4784 MAKE_ENTRY(io_wait); 4785 #endif 4786 #if (DBVER >= 48) 4787 MAKE_ENTRY(sync_interrupted); 4788 #endif 4789 4790 #undef MAKE_ENTRY 4791 free(gsp); 4792 4793 d2 = PyDict_New(); 4794 if (d2 == NULL) { 4795 Py_DECREF(d); 4796 if (fsp) 4797 free(fsp); 4798 return NULL; 4799 } 4800 #define MAKE_ENTRY(name) _addIntToDict(d3, #name, (*fsp2)->st_##name) 4801 for(fsp2=fsp;*fsp2; fsp2++) { 4802 d3 = PyDict_New(); 4803 if (d3 == NULL) { 4804 Py_DECREF(d); 4805 Py_DECREF(d2); 4806 if (fsp) 4807 free(fsp); 4808 return NULL; 4809 } 4810 MAKE_ENTRY(pagesize); 4811 MAKE_ENTRY(cache_hit); 4812 MAKE_ENTRY(cache_miss); 4813 MAKE_ENTRY(map); 4814 MAKE_ENTRY(page_create); 4815 MAKE_ENTRY(page_in); 4816 MAKE_ENTRY(page_out); 4817 if(PyDict_SetItemString(d2, (*fsp2)->file_name, d3)) { 4818 Py_DECREF(d); 4819 Py_DECREF(d2); 4820 Py_DECREF(d3); 4821 if (fsp) 4822 free(fsp); 4823 return NULL; 4824 } 4825 Py_DECREF(d3); 4826 } 4827 4828 #undef MAKE_ENTRY 4829 free(fsp); 4830 4831 r = Py_BuildValue("(OO)", d, d2); 4832 Py_DECREF(d); 4833 Py_DECREF(d2); 4834 return r; 4835 } 4836 4837 #if (DBVER >= 43) 4838 static PyObject* 4839 DBEnv_memp_stat_print(DBEnvObject* self, PyObject* args, PyObject *kwargs) 4840 { 4841 int err; 4842 int flags=0; 4843 static char* kwnames[] = { "flags", NULL }; 4844 4845 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:memp_stat_print", 4846 kwnames, &flags)) 4847 { 4848 return NULL; 4849 } 4850 CHECK_ENV_NOT_CLOSED(self); 4851 MYDB_BEGIN_ALLOW_THREADS; 4852 err = self->db_env->memp_stat_print(self->db_env, flags); 4853 MYDB_END_ALLOW_THREADS; 4854 RETURN_IF_ERR(); 4855 RETURN_NONE(); 4856 } 4857 #endif 4858 4859 4860 static PyObject* 4861 DBEnv_memp_trickle(DBEnvObject* self, PyObject* args) 4862 { 4863 int err, percent, nwrotep; 4864 4865 if (!PyArg_ParseTuple(args, "i:memp_trickle", &percent)) 4866 return NULL; 4867 CHECK_ENV_NOT_CLOSED(self); 4868 MYDB_BEGIN_ALLOW_THREADS; 4869 err = self->db_env->memp_trickle(self->db_env, percent, &nwrotep); 4870 MYDB_END_ALLOW_THREADS; 4871 RETURN_IF_ERR(); 4872 return NUMBER_FromLong(nwrotep); 4873 } 4874 4875 static PyObject* 4876 DBEnv_memp_sync(DBEnvObject* self, PyObject* args) 4877 { 4878 int err; 4879 DB_LSN lsn = {0, 0}; 4880 DB_LSN *lsn_p = NULL; 4881 4882 if (!PyArg_ParseTuple(args, "|(ii):memp_sync", &lsn.file, &lsn.offset)) 4883 return NULL; 4884 if ((lsn.file!=0) || (lsn.offset!=0)) { 4885 lsn_p = &lsn; 4886 } 4887 CHECK_ENV_NOT_CLOSED(self); 4888 MYDB_BEGIN_ALLOW_THREADS; 4889 err = self->db_env->memp_sync(self->db_env, lsn_p); 4890 MYDB_END_ALLOW_THREADS; 4891 RETURN_IF_ERR(); 4892 RETURN_NONE(); 4893 } 4894 4895 static PyObject* 4083 4896 DBEnv_remove(DBEnvObject* self, PyObject* args) 4084 4897 { … … 4096 4909 } 4097 4910 4098 #if (DBVER >= 41)4099 4911 static PyObject* 4100 4912 DBEnv_dbremove(DBEnvObject* self, PyObject* args, PyObject* kwargs) … … 4110 4922 4111 4923 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s|zOi:dbremove", kwnames, 4112 4113 4924 &file, &database, &txnobj, &flags)) { 4925 return NULL; 4114 4926 } 4115 4927 if (!checkTxnObj(txnobj, &txn)) { … … 4138 4950 4139 4951 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "szs|Oi:dbrename", kwnames, 4140 4141 4952 &file, &database, &newname, &txnobj, &flags)) { 4953 return NULL; 4142 4954 } 4143 4955 if (!checkTxnObj(txnobj, &txn)) { … … 4152 4964 RETURN_NONE(); 4153 4965 } 4966 4967 4154 4968 4155 4969 static PyObject* … … 4162 4976 4163 4977 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s|i:set_encrypt", kwnames, 4164 4165 4978 &passwd, &flags)) { 4979 return NULL; 4166 4980 } 4167 4981 … … 4173 4987 RETURN_NONE(); 4174 4988 } 4175 #endif /* DBVER >= 41 */ 4989 4990 #if (DBVER >= 42) 4991 static PyObject* 4992 DBEnv_get_encrypt_flags(DBEnvObject* self) 4993 { 4994 int err; 4995 u_int32_t flags; 4996 4997 CHECK_ENV_NOT_CLOSED(self); 4998 4999 MYDB_BEGIN_ALLOW_THREADS; 5000 err = self->db_env->get_encrypt_flags(self->db_env, &flags); 5001 MYDB_END_ALLOW_THREADS; 5002 5003 RETURN_IF_ERR(); 5004 5005 return NUMBER_FromLong(flags); 5006 } 5007 5008 static PyObject* 5009 DBEnv_get_timeout(DBEnvObject* self, PyObject* args, PyObject* kwargs) 5010 { 5011 int err; 5012 int flag; 5013 u_int32_t timeout; 5014 static char* kwnames[] = {"flag", NULL }; 5015 5016 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i:get_timeout", kwnames, 5017 &flag)) { 5018 return NULL; 5019 } 5020 CHECK_ENV_NOT_CLOSED(self); 5021 5022 MYDB_BEGIN_ALLOW_THREADS; 5023 err = self->db_env->get_timeout(self->db_env, &timeout, flag); 5024 MYDB_END_ALLOW_THREADS; 5025 RETURN_IF_ERR(); 5026 return NUMBER_FromLong(timeout); 5027 } 5028 #endif 5029 4176 5030 4177 5031 static PyObject* … … 4184 5038 4185 5039 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "ii:set_timeout", kwnames, 4186 4187 5040 &timeout, &flags)) { 5041 return NULL; 4188 5042 } 4189 5043 … … 4210 5064 RETURN_NONE(); 4211 5065 } 5066 5067 #if (DBVER >= 42) 5068 static PyObject* 5069 DBEnv_get_shm_key(DBEnvObject* self) 5070 { 5071 int err; 5072 long shm_key; 5073 5074 CHECK_ENV_NOT_CLOSED(self); 5075 5076 MYDB_BEGIN_ALLOW_THREADS; 5077 err = self->db_env->get_shm_key(self->db_env, &shm_key); 5078 MYDB_END_ALLOW_THREADS; 5079 5080 RETURN_IF_ERR(); 5081 5082 return NUMBER_FromLong(shm_key); 5083 } 5084 #endif 5085 5086 #if (DBVER >= 46) 5087 static PyObject* 5088 DBEnv_set_cache_max(DBEnvObject* self, PyObject* args) 5089 { 5090 int err, gbytes, bytes; 5091 5092 if (!PyArg_ParseTuple(args, "ii:set_cache_max", 5093 &gbytes, &bytes)) 5094 return NULL; 5095 CHECK_ENV_NOT_CLOSED(self); 5096 5097 MYDB_BEGIN_ALLOW_THREADS; 5098 err = self->db_env->set_cache_max(self->db_env, gbytes, bytes); 5099 MYDB_END_ALLOW_THREADS; 5100 RETURN_IF_ERR(); 5101 RETURN_NONE(); 5102 } 5103 5104 static PyObject* 5105 DBEnv_get_cache_max(DBEnvObject* self) 5106 { 5107 int err; 5108 u_int32_t gbytes, bytes; 5109 5110 CHECK_ENV_NOT_CLOSED(self); 5111 5112 MYDB_BEGIN_ALLOW_THREADS; 5113 err = self->db_env->get_cache_max(self->db_env, &gbytes, &bytes); 5114 MYDB_END_ALLOW_THREADS; 5115 5116 RETURN_IF_ERR(); 5117 5118 return Py_BuildValue("(ii)", gbytes, bytes); 5119 } 5120 #endif 5121 5122 #if (DBVER >= 46) 5123 static PyObject* 5124 DBEnv_set_thread_count(DBEnvObject* self, PyObject* args) 5125 { 5126 int err; 5127 u_int32_t count; 5128 5129 if (!PyArg_ParseTuple(args, "i:set_thread_count", &count)) 5130 return NULL; 5131 CHECK_ENV_NOT_CLOSED(self); 5132 5133 MYDB_BEGIN_ALLOW_THREADS; 5134 err = self->db_env->set_thread_count(self->db_env, count); 5135 MYDB_END_ALLOW_THREADS; 5136 RETURN_IF_ERR(); 5137 RETURN_NONE(); 5138 } 5139 5140 static PyObject* 5141 DBEnv_get_thread_count(DBEnvObject* self) 5142 { 5143 int err; 5144 u_int32_t count; 5145 5146 CHECK_ENV_NOT_CLOSED(self); 5147 5148 MYDB_BEGIN_ALLOW_THREADS; 5149 err = self->db_env->get_thread_count(self->db_env, &count); 5150 MYDB_END_ALLOW_THREADS; 5151 RETURN_IF_ERR(); 5152 return NUMBER_FromLong(count); 5153 } 5154 #endif 4212 5155 4213 5156 static PyObject* … … 4228 5171 } 4229 5172 5173 #if (DBVER >= 42) 5174 static PyObject* 5175 DBEnv_get_cachesize(DBEnvObject* self) 5176 { 5177 int err; 5178 u_int32_t gbytes, bytes; 5179 int ncache; 5180 5181 CHECK_ENV_NOT_CLOSED(self); 5182 5183 MYDB_BEGIN_ALLOW_THREADS; 5184 err = self->db_env->get_cachesize(self->db_env, &gbytes, &bytes, &ncache); 5185 MYDB_END_ALLOW_THREADS; 5186 5187 RETURN_IF_ERR(); 5188 5189 return Py_BuildValue("(iii)", gbytes, bytes, ncache); 5190 } 5191 #endif 5192 4230 5193 4231 5194 static PyObject* … … 4246 5209 } 4247 5210 5211 #if (DBVER >= 42) 5212 static PyObject* 5213 DBEnv_get_flags(DBEnvObject* self) 5214 { 5215 int err; 5216 u_int32_t flags; 5217 5218 CHECK_ENV_NOT_CLOSED(self); 5219 5220 MYDB_BEGIN_ALLOW_THREADS; 5221 err = self->db_env->get_flags(self->db_env, &flags); 5222 MYDB_END_ALLOW_THREADS; 5223 RETURN_IF_ERR(); 5224 return NUMBER_FromLong(flags); 5225 } 5226 #endif 4248 5227 4249 5228 #if (DBVER >= 47) … … 4264 5243 RETURN_NONE(); 4265 5244 } 5245 5246 static PyObject* 5247 DBEnv_log_get_config(DBEnvObject* self, PyObject* args) 5248 { 5249 int err, flag, onoff; 5250 5251 if (!PyArg_ParseTuple(args, "i:log_get_config", &flag)) 5252 return NULL; 5253 CHECK_ENV_NOT_CLOSED(self); 5254 5255 MYDB_BEGIN_ALLOW_THREADS; 5256 err = self->db_env->log_get_config(self->db_env, flag, &onoff); 5257 MYDB_END_ALLOW_THREADS; 5258 RETURN_IF_ERR(); 5259 return PyBool_FromLong(onoff); 5260 } 4266 5261 #endif /* DBVER >= 47 */ 4267 5262 5263 #if (DBVER >= 44) 5264 static PyObject* 5265 DBEnv_mutex_set_max(DBEnvObject* self, PyObject* args) 5266 { 5267 int err; 5268 int value; 5269 5270 if (!PyArg_ParseTuple(args, "i:mutex_set_max", &value)) 5271 return NULL; 5272 5273 CHECK_ENV_NOT_CLOSED(self); 5274 5275 MYDB_BEGIN_ALLOW_THREADS; 5276 err = self->db_env->mutex_set_max(self->db_env, value); 5277 MYDB_END_ALLOW_THREADS; 5278 5279 RETURN_IF_ERR(); 5280 RETURN_NONE(); 5281 } 5282 5283 static PyObject* 5284 DBEnv_mutex_get_max(DBEnvObject* self) 5285 { 5286 int err; 5287 u_int32_t value; 5288 5289 CHECK_ENV_NOT_CLOSED(self); 5290 5291 MYDB_BEGIN_ALLOW_THREADS; 5292 err = self->db_env->mutex_get_max(self->db_env, &value); 5293 MYDB_END_ALLOW_THREADS; 5294 5295 RETURN_IF_ERR(); 5296 5297 return NUMBER_FromLong(value); 5298 } 5299 5300 static PyObject* 5301 DBEnv_mutex_set_align(DBEnvObject* self, PyObject* args) 5302 { 5303 int err; 5304 int align; 5305 5306 if (!PyArg_ParseTuple(args, "i:mutex_set_align", &align)) 5307 return NULL; 5308 5309 CHECK_ENV_NOT_CLOSED(self); 5310 5311 MYDB_BEGIN_ALLOW_THREADS; 5312 err = self->db_env->mutex_set_align(self->db_env, align); 5313 MYDB_END_ALLOW_THREADS; 5314 5315 RETURN_IF_ERR(); 5316 RETURN_NONE(); 5317 } 5318 5319 static PyObject* 5320 DBEnv_mutex_get_align(DBEnvObject* self) 5321 { 5322 int err; 5323 u_int32_t align; 5324 5325 CHECK_ENV_NOT_CLOSED(self); 5326 5327 MYDB_BEGIN_ALLOW_THREADS; 5328 err = self->db_env->mutex_get_align(self->db_env, &align); 5329 MYDB_END_ALLOW_THREADS; 5330 5331 RETURN_IF_ERR(); 5332 5333 return NUMBER_FromLong(align); 5334 } 5335 5336 static PyObject* 5337 DBEnv_mutex_set_increment(DBEnvObject* self, PyObject* args) 5338 { 5339 int err; 5340 int increment; 5341 5342 if (!PyArg_ParseTuple(args, "i:mutex_set_increment", &increment)) 5343 return NULL; 5344 5345 CHECK_ENV_NOT_CLOSED(self); 5346 5347 MYDB_BEGIN_ALLOW_THREADS; 5348 err = self->db_env->mutex_set_increment(self->db_env, increment); 5349 MYDB_END_ALLOW_THREADS; 5350 5351 RETURN_IF_ERR(); 5352 RETURN_NONE(); 5353 } 5354 5355 static PyObject* 5356 DBEnv_mutex_get_increment(DBEnvObject* self) 5357 { 5358 int err; 5359 u_int32_t increment; 5360 5361 CHECK_ENV_NOT_CLOSED(self); 5362 5363 MYDB_BEGIN_ALLOW_THREADS; 5364 err = self->db_env->mutex_get_increment(self->db_env, &increment); 5365 MYDB_END_ALLOW_THREADS; 5366 5367 RETURN_IF_ERR(); 5368 5369 return NUMBER_FromLong(increment); 5370 } 5371 5372 static PyObject* 5373 DBEnv_mutex_set_tas_spins(DBEnvObject* self, PyObject* args) 5374 { 5375 int err; 5376 int tas_spins; 5377 5378 if (!PyArg_ParseTuple(args, "i:mutex_set_tas_spins", &tas_spins)) 5379 return NULL; 5380 5381 CHECK_ENV_NOT_CLOSED(self); 5382 5383 MYDB_BEGIN_ALLOW_THREADS; 5384 err = self->db_env->mutex_set_tas_spins(self->db_env, tas_spins); 5385 MYDB_END_ALLOW_THREADS; 5386 5387 RETURN_IF_ERR(); 5388 RETURN_NONE(); 5389 } 5390 5391 static PyObject* 5392 DBEnv_mutex_get_tas_spins(DBEnvObject* self) 5393 { 5394 int err; 5395 u_int32_t tas_spins; 5396 5397 CHECK_ENV_NOT_CLOSED(self); 5398 5399 MYDB_BEGIN_ALLOW_THREADS; 5400 err = self->db_env->mutex_get_tas_spins(self->db_env, &tas_spins); 5401 MYDB_END_ALLOW_THREADS; 5402 5403 RETURN_IF_ERR(); 5404 5405 return NUMBER_FromLong(tas_spins); 5406 } 5407 #endif 4268 5408 4269 5409 static PyObject* … … 4284 5424 } 4285 5425 5426 #if (DBVER >= 42) 5427 static PyObject* 5428 DBEnv_get_data_dirs(DBEnvObject* self) 5429 { 5430 int err; 5431 PyObject *tuple; 5432 PyObject *item; 5433 const char **dirpp; 5434 int size, i; 5435 5436 CHECK_ENV_NOT_CLOSED(self); 5437 5438 MYDB_BEGIN_ALLOW_THREADS; 5439 err = self->db_env->get_data_dirs(self->db_env, &dirpp); 5440 MYDB_END_ALLOW_THREADS; 5441 5442 RETURN_IF_ERR(); 5443 5444 /* 5445 ** Calculate size. Python C API 5446 ** actually allows for tuple resizing, 5447 ** but this is simple enough. 5448 */ 5449 for (size=0; *(dirpp+size) ; size++); 5450 5451 tuple = PyTuple_New(size); 5452 if (!tuple) 5453 return NULL; 5454 5455 for (i=0; i<size; i++) { 5456 item = PyBytes_FromString (*(dirpp+i)); 5457 if (item == NULL) { 5458 Py_DECREF(tuple); 5459 tuple = NULL; 5460 break; 5461 } 5462 PyTuple_SET_ITEM(tuple, i, item); 5463 } 5464 return tuple; 5465 } 5466 #endif 5467 5468 #if (DBVER >= 44) 5469 static PyObject* 5470 DBEnv_set_lg_filemode(DBEnvObject* self, PyObject* args) 5471 { 5472 int err, filemode; 5473 5474 if (!PyArg_ParseTuple(args, "i:set_lg_filemode", &filemode)) 5475 return NULL; 5476 CHECK_ENV_NOT_CLOSED(self); 5477 5478 MYDB_BEGIN_ALLOW_THREADS; 5479 err = self->db_env->set_lg_filemode(self->db_env, filemode); 5480 MYDB_END_ALLOW_THREADS; 5481 RETURN_IF_ERR(); 5482 RETURN_NONE(); 5483 } 5484 5485 static PyObject* 5486 DBEnv_get_lg_filemode(DBEnvObject* self) 5487 { 5488 int err, filemode; 5489 5490 CHECK_ENV_NOT_CLOSED(self); 5491 5492 MYDB_BEGIN_ALLOW_THREADS; 5493 err = self->db_env->get_lg_filemode(self->db_env, &filemode); 5494 MYDB_END_ALLOW_THREADS; 5495 RETURN_IF_ERR(); 5496 return NUMBER_FromLong(filemode); 5497 } 5498 #endif 4286 5499 4287 5500 static PyObject* … … 4301 5514 } 4302 5515 5516 #if (DBVER >= 42) 5517 static PyObject* 5518 DBEnv_get_lg_bsize(DBEnvObject* self) 5519 { 5520 int err; 5521 u_int32_t lg_bsize; 5522 5523 CHECK_ENV_NOT_CLOSED(self); 5524 5525 MYDB_BEGIN_ALLOW_THREADS; 5526 err = self->db_env->get_lg_bsize(self->db_env, &lg_bsize); 5527 MYDB_END_ALLOW_THREADS; 5528 RETURN_IF_ERR(); 5529 return NUMBER_FromLong(lg_bsize); 5530 } 5531 #endif 4303 5532 4304 5533 static PyObject* … … 4319 5548 } 4320 5549 5550 #if (DBVER >= 42) 5551 static PyObject* 5552 DBEnv_get_lg_dir(DBEnvObject* self) 5553 { 5554 int err; 5555 const char *dirp; 5556 5557 CHECK_ENV_NOT_CLOSED(self); 5558 5559 MYDB_BEGIN_ALLOW_THREADS; 5560 err = self->db_env->get_lg_dir(self->db_env, &dirp); 5561 MYDB_END_ALLOW_THREADS; 5562 RETURN_IF_ERR(); 5563 return PyBytes_FromString(dirp); 5564 } 5565 #endif 5566 4321 5567 static PyObject* 4322 5568 DBEnv_set_lg_max(DBEnvObject* self, PyObject* args) … … 4369 5615 } 4370 5616 5617 #if (DBVER >= 42) 5618 static PyObject* 5619 DBEnv_get_lg_regionmax(DBEnvObject* self) 5620 { 5621 int err; 5622 u_int32_t lg_regionmax; 5623 5624 CHECK_ENV_NOT_CLOSED(self); 5625 5626 MYDB_BEGIN_ALLOW_THREADS; 5627 err = self->db_env->get_lg_regionmax(self->db_env, &lg_regionmax); 5628 MYDB_END_ALLOW_THREADS; 5629 RETURN_IF_ERR(); 5630 return NUMBER_FromLong(lg_regionmax); 5631 } 5632 #endif 5633 5634 #if (DBVER >= 47) 5635 static PyObject* 5636 DBEnv_set_lk_partitions(DBEnvObject* self, PyObject* args) 5637 { 5638 int err, lk_partitions; 5639 5640 if (!PyArg_ParseTuple(args, "i:set_lk_partitions", &lk_partitions)) 5641 return NULL; 5642 CHECK_ENV_NOT_CLOSED(self); 5643 5644 MYDB_BEGIN_ALLOW_THREADS; 5645 err = self->db_env->set_lk_partitions(self->db_env, lk_partitions); 5646 MYDB_END_ALLOW_THREADS; 5647 RETURN_IF_ERR(); 5648 RETURN_NONE(); 5649 } 5650 5651 static PyObject* 5652 DBEnv_get_lk_partitions(DBEnvObject* self) 5653 { 5654 int err; 5655 u_int32_t lk_partitions; 5656 5657 CHECK_ENV_NOT_CLOSED(self); 5658 5659 MYDB_BEGIN_ALLOW_THREADS; 5660 err = self->db_env->get_lk_partitions(self->db_env, &lk_partitions); 5661 MYDB_END_ALLOW_THREADS; 5662 RETURN_IF_ERR(); 5663 return NUMBER_FromLong(lk_partitions); 5664 } 5665 #endif 4371 5666 4372 5667 static PyObject* … … 4386 5681 } 4387 5682 5683 #if (DBVER >= 42) 5684 static PyObject* 5685 DBEnv_get_lk_detect(DBEnvObject* self) 5686 { 5687 int err; 5688 u_int32_t lk_detect; 5689 5690 CHECK_ENV_NOT_CLOSED(self); 5691 5692 MYDB_BEGIN_ALLOW_THREADS; 5693 err = self->db_env->get_lk_detect(self->db_env, &lk_detect); 5694 MYDB_END_ALLOW_THREADS; 5695 RETURN_IF_ERR(); 5696 return NUMBER_FromLong(lk_detect); 5697 } 5698 #endif 5699 4388 5700 4389 5701 #if (DBVER < 45) … … 4423 5735 } 4424 5736 5737 #if (DBVER >= 42) 5738 static PyObject* 5739 DBEnv_get_lk_max_locks(DBEnvObject* self) 5740 { 5741 int err; 5742 u_int32_t lk_max; 5743 5744 CHECK_ENV_NOT_CLOSED(self); 5745 5746 MYDB_BEGIN_ALLOW_THREADS; 5747 err = self->db_env->get_lk_max_locks(self->db_env, &lk_max); 5748 MYDB_END_ALLOW_THREADS; 5749 RETURN_IF_ERR(); 5750 return NUMBER_FromLong(lk_max); 5751 } 5752 #endif 4425 5753 4426 5754 static PyObject* … … 4440 5768 } 4441 5769 5770 #if (DBVER >= 42) 5771 static PyObject* 5772 DBEnv_get_lk_max_lockers(DBEnvObject* self) 5773 { 5774 int err; 5775 u_int32_t lk_max; 5776 5777 CHECK_ENV_NOT_CLOSED(self); 5778 5779 MYDB_BEGIN_ALLOW_THREADS; 5780 err = self->db_env->get_lk_max_lockers(self->db_env, &lk_max); 5781 MYDB_END_ALLOW_THREADS; 5782 RETURN_IF_ERR(); 5783 return NUMBER_FromLong(lk_max); 5784 } 5785 #endif 4442 5786 4443 5787 static PyObject* … … 4457 5801 } 4458 5802 5803 #if (DBVER >= 42) 5804 static PyObject* 5805 DBEnv_get_lk_max_objects(DBEnvObject* self) 5806 { 5807 int err; 5808 u_int32_t lk_max; 5809 5810 CHECK_ENV_NOT_CLOSED(self); 5811 5812 MYDB_BEGIN_ALLOW_THREADS; 5813 err = self->db_env->get_lk_max_objects(self->db_env, &lk_max); 5814 MYDB_END_ALLOW_THREADS; 5815 RETURN_IF_ERR(); 5816 return NUMBER_FromLong(lk_max); 5817 } 5818 #endif 5819 5820 #if (DBVER >= 42) 5821 static PyObject* 5822 DBEnv_get_mp_mmapsize(DBEnvObject* self) 5823 { 5824 int err; 5825 size_t mmapsize; 5826 5827 CHECK_ENV_NOT_CLOSED(self); 5828 5829 MYDB_BEGIN_ALLOW_THREADS; 5830 err = self->db_env->get_mp_mmapsize(self->db_env, &mmapsize); 5831 MYDB_END_ALLOW_THREADS; 5832 RETURN_IF_ERR(); 5833 return NUMBER_FromLong(mmapsize); 5834 } 5835 #endif 5836 4459 5837 4460 5838 static PyObject* … … 4491 5869 RETURN_NONE(); 4492 5870 } 5871 5872 5873 #if (DBVER >= 42) 5874 static PyObject* 5875 DBEnv_get_tmp_dir(DBEnvObject* self) 5876 { 5877 int err; 5878 const char *dirpp; 5879 5880 CHECK_ENV_NOT_CLOSED(self); 5881 5882 MYDB_BEGIN_ALLOW_THREADS; 5883 err = self->db_env->get_tmp_dir(self->db_env, &dirpp); 5884 MYDB_END_ALLOW_THREADS; 5885 5886 RETURN_IF_ERR(); 5887 5888 return PyBytes_FromString(dirpp); 5889 } 5890 #endif 4493 5891 4494 5892 … … 4502 5900 #define PREPLIST_LEN 16 4503 5901 DB_PREPLIST preplist[PREPLIST_LEN]; 5902 #if (DBVER < 48) 4504 5903 long retp; 5904 #else 5905 u_int32_t retp; 5906 #endif 4505 5907 4506 5908 CHECK_ENV_NOT_CLOSED(self); … … 4523 5925 for (i=0; i<retp; i++) { 4524 5926 gid=PyBytes_FromStringAndSize((char *)(preplist[i].gid), 4525 DB_ XIDDATASIZE);5927 DB_GID_SIZE); 4526 5928 if (!gid) { 4527 5929 Py_DECREF(list); 4528 5930 return NULL; 4529 5931 } 4530 txn=newDBTxnObject(self, NULL, preplist[i].txn, flags);5932 txn=newDBTxnObject(self, NULL, preplist[i].txn, 0); 4531 5933 if (!txn) { 4532 5934 Py_DECREF(list); … … 4603 6005 4604 6006 6007 #if (DBVER >= 42) 6008 static PyObject* 6009 DBEnv_get_tx_max(DBEnvObject* self) 6010 { 6011 int err; 6012 u_int32_t max; 6013 6014 CHECK_ENV_NOT_CLOSED(self); 6015 6016 MYDB_BEGIN_ALLOW_THREADS; 6017 err = self->db_env->get_tx_max(self->db_env, &max); 6018 MYDB_END_ALLOW_THREADS; 6019 RETURN_IF_ERR(); 6020 return PyLong_FromUnsignedLong(max); 6021 } 6022 #endif 6023 6024 4605 6025 static PyObject* 4606 6026 DBEnv_set_tx_max(DBEnvObject* self, PyObject* args) … … 4612 6032 CHECK_ENV_NOT_CLOSED(self); 4613 6033 6034 MYDB_BEGIN_ALLOW_THREADS; 4614 6035 err = self->db_env->set_tx_max(self->db_env, max); 4615 RETURN_IF_ERR(); 4616 RETURN_NONE(); 4617 } 4618 6036 MYDB_END_ALLOW_THREADS; 6037 RETURN_IF_ERR(); 6038 RETURN_NONE(); 6039 } 6040 6041 6042 #if (DBVER >= 42) 6043 static PyObject* 6044 DBEnv_get_tx_timestamp(DBEnvObject* self) 6045 { 6046 int err; 6047 time_t timestamp; 6048 6049 CHECK_ENV_NOT_CLOSED(self); 6050 6051 MYDB_BEGIN_ALLOW_THREADS; 6052 err = self->db_env->get_tx_timestamp(self->db_env, ×tamp); 6053 MYDB_END_ALLOW_THREADS; 6054 RETURN_IF_ERR(); 6055 return NUMBER_FromLong(timestamp); 6056 } 6057 #endif 4619 6058 4620 6059 static PyObject* … … 4629 6068 CHECK_ENV_NOT_CLOSED(self); 4630 6069 timestamp = (time_t)stamp; 6070 MYDB_BEGIN_ALLOW_THREADS; 4631 6071 err = self->db_env->set_tx_timestamp(self->db_env, ×tamp); 6072 MYDB_END_ALLOW_THREADS; 4632 6073 RETURN_IF_ERR(); 4633 6074 RETURN_NONE(); … … 4723 6164 #if (DBVER >= 44) 4724 6165 static PyObject* 4725 DBEnv_ lsn_reset(DBEnvObject* self, PyObject* args, PyObject* kwargs)6166 DBEnv_fileid_reset(DBEnvObject* self, PyObject* args, PyObject* kwargs) 4726 6167 { 4727 6168 int err; … … 4730 6171 static char* kwnames[] = { "file", "flags", NULL}; 4731 6172 6173 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "z|i:fileid_reset", kwnames, 6174 &file, &flags)) 6175 return NULL; 6176 CHECK_ENV_NOT_CLOSED(self); 6177 6178 MYDB_BEGIN_ALLOW_THREADS; 6179 err = self->db_env->fileid_reset(self->db_env, file, flags); 6180 MYDB_END_ALLOW_THREADS; 6181 RETURN_IF_ERR(); 6182 RETURN_NONE(); 6183 } 6184 6185 static PyObject* 6186 DBEnv_lsn_reset(DBEnvObject* self, PyObject* args, PyObject* kwargs) 6187 { 6188 int err; 6189 char *file; 6190 u_int32_t flags = 0; 6191 static char* kwnames[] = { "file", "flags", NULL}; 6192 4732 6193 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "z|i:lsn_reset", kwnames, 4733 6194 &file, &flags)) … … 4742 6203 } 4743 6204 #endif /* DBVER >= 4.4 */ 6205 6206 6207 #if (DBVER >= 43) 6208 static PyObject* 6209 DBEnv_stat_print(DBEnvObject* self, PyObject* args, PyObject *kwargs) 6210 { 6211 int err; 6212 int flags=0; 6213 static char* kwnames[] = { "flags", NULL }; 6214 6215 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:stat_print", 6216 kwnames, &flags)) 6217 { 6218 return NULL; 6219 } 6220 CHECK_ENV_NOT_CLOSED(self); 6221 MYDB_BEGIN_ALLOW_THREADS; 6222 err = self->db_env->stat_print(self->db_env, flags); 6223 MYDB_END_ALLOW_THREADS; 6224 RETURN_IF_ERR(); 6225 RETURN_NONE(); 6226 } 6227 #endif 6228 4744 6229 4745 6230 static PyObject* … … 4777 6262 MAKE_ENTRY(lg_size); 4778 6263 MAKE_ENTRY(record); 4779 #endif4780 #if (DBVER < 41)4781 MAKE_ENTRY(lg_max);4782 6264 #endif 4783 6265 MAKE_ENTRY(w_mbytes); … … 4807 6289 4808 6290 6291 #if (DBVER >= 43) 6292 static PyObject* 6293 DBEnv_log_stat_print(DBEnvObject* self, PyObject* args, PyObject *kwargs) 6294 { 6295 int err; 6296 int flags=0; 6297 static char* kwnames[] = { "flags", NULL }; 6298 6299 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:log_stat_print", 6300 kwnames, &flags)) 6301 { 6302 return NULL; 6303 } 6304 CHECK_ENV_NOT_CLOSED(self); 6305 MYDB_BEGIN_ALLOW_THREADS; 6306 err = self->db_env->log_stat_print(self->db_env, flags); 6307 MYDB_END_ALLOW_THREADS; 6308 RETURN_IF_ERR(); 6309 RETURN_NONE(); 6310 } 6311 #endif 6312 6313 4809 6314 static PyObject* 4810 6315 DBEnv_lock_stat(DBEnvObject* self, PyObject* args) … … 4833 6338 #define MAKE_ENTRY(name) _addIntToDict(d, #name, sp->st_##name) 4834 6339 4835 #if (DBVER < 41)4836 MAKE_ENTRY(lastid);4837 #endif4838 #if (DBVER >=41)4839 6340 MAKE_ENTRY(id); 4840 6341 MAKE_ENTRY(cur_maxid); 4841 #endif4842 6342 MAKE_ENTRY(nmodes); 4843 6343 MAKE_ENTRY(maxlocks); … … 4864 6364 #endif 4865 6365 MAKE_ENTRY(ndeadlocks); 4866 #if (DBVER >= 41)4867 6366 MAKE_ENTRY(locktimeout); 4868 6367 MAKE_ENTRY(txntimeout); 4869 #endif4870 6368 MAKE_ENTRY(nlocktimeouts); 4871 6369 MAKE_ENTRY(ntxntimeouts); … … 4893 6391 } 4894 6392 6393 #if (DBVER >= 43) 6394 static PyObject* 6395 DBEnv_lock_stat_print(DBEnvObject* self, PyObject* args, PyObject *kwargs) 6396 { 6397 int err; 6398 int flags=0; 6399 static char* kwnames[] = { "flags", NULL }; 6400 6401 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:lock_stat_print", 6402 kwnames, &flags)) 6403 { 6404 return NULL; 6405 } 6406 CHECK_ENV_NOT_CLOSED(self); 6407 MYDB_BEGIN_ALLOW_THREADS; 6408 err = self->db_env->lock_stat_print(self->db_env, flags); 6409 MYDB_END_ALLOW_THREADS; 6410 RETURN_IF_ERR(); 6411 RETURN_NONE(); 6412 } 6413 #endif 6414 6415 6416 static PyObject* 6417 DBEnv_log_cursor(DBEnvObject* self) 6418 { 6419 int err; 6420 DB_LOGC* dblogc; 6421 6422 CHECK_ENV_NOT_CLOSED(self); 6423 6424 MYDB_BEGIN_ALLOW_THREADS; 6425 err = self->db_env->log_cursor(self->db_env, &dblogc, 0); 6426 MYDB_END_ALLOW_THREADS; 6427 RETURN_IF_ERR(); 6428 return (PyObject*) newDBLogCursorObject(dblogc, self); 6429 } 6430 6431 4895 6432 static PyObject* 4896 6433 DBEnv_log_flush(DBEnvObject* self) … … 4907 6444 RETURN_NONE(); 4908 6445 } 6446 6447 static PyObject* 6448 DBEnv_log_file(DBEnvObject* self, PyObject* args) 6449 { 6450 int err; 6451 DB_LSN lsn = {0, 0}; 6452 int size = 20; 6453 char *name = NULL; 6454 PyObject *retval; 6455 6456 if (!PyArg_ParseTuple(args, "(ii):log_file", &lsn.file, &lsn.offset)) 6457 return NULL; 6458 6459 CHECK_ENV_NOT_CLOSED(self); 6460 6461 do { 6462 name = malloc(size); 6463 if (!name) { 6464 PyErr_NoMemory(); 6465 return NULL; 6466 } 6467 MYDB_BEGIN_ALLOW_THREADS; 6468 err = self->db_env->log_file(self->db_env, &lsn, name, size); 6469 MYDB_END_ALLOW_THREADS; 6470 if (err == EINVAL) { 6471 free(name); 6472 size *= 2; 6473 } else if (err) { 6474 free(name); 6475 RETURN_IF_ERR(); 6476 assert(0); /* Unreachable... supposely */ 6477 return NULL; 6478 } 6479 /* 6480 ** If the final buffer we try is too small, we will 6481 ** get this exception: 6482 ** DBInvalidArgError: 6483 ** (22, 'Invalid argument -- DB_ENV->log_file: name buffer is too short') 6484 */ 6485 } while ((err == EINVAL) && (size<(1<<17))); 6486 6487 RETURN_IF_ERR(); /* Maybe the size is not the problem */ 6488 6489 retval = Py_BuildValue("s", name); 6490 free(name); 6491 return retval; 6492 } 6493 6494 6495 #if (DBVER >= 44) 6496 static PyObject* 6497 DBEnv_log_printf(DBEnvObject* self, PyObject* args, PyObject *kwargs) 6498 { 6499 int err; 6500 char *string; 6501 PyObject *txnobj = NULL; 6502 DB_TXN *txn = NULL; 6503 static char* kwnames[] = {"string", "txn", NULL }; 6504 6505 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "s|O:log_printf", kwnames, 6506 &string, &txnobj)) 6507 return NULL; 6508 6509 CHECK_ENV_NOT_CLOSED(self); 6510 6511 if (!checkTxnObj(txnobj, &txn)) 6512 return NULL; 6513 6514 /* 6515 ** Do not use the format string directly, to avoid attacks. 6516 */ 6517 MYDB_BEGIN_ALLOW_THREADS; 6518 err = self->db_env->log_printf(self->db_env, txn, "%s", string); 6519 MYDB_END_ALLOW_THREADS; 6520 6521 RETURN_IF_ERR(); 6522 RETURN_NONE(); 6523 } 6524 #endif 6525 4909 6526 4910 6527 static PyObject* … … 4956 6573 4957 6574 6575 #if (DBVER >= 44) 6576 static PyObject* 6577 DBEnv_mutex_stat(DBEnvObject* self, PyObject* args) 6578 { 6579 int err; 6580 DB_MUTEX_STAT* statp = NULL; 6581 PyObject* d = NULL; 6582 u_int32_t flags = 0; 6583 6584 if (!PyArg_ParseTuple(args, "|i:mutex_stat", &flags)) 6585 return NULL; 6586 CHECK_ENV_NOT_CLOSED(self); 6587 6588 MYDB_BEGIN_ALLOW_THREADS; 6589 err = self->db_env->mutex_stat(self->db_env, &statp, flags); 6590 MYDB_END_ALLOW_THREADS; 6591 RETURN_IF_ERR(); 6592 6593 /* Turn the stat structure into a dictionary */ 6594 d = PyDict_New(); 6595 if (d == NULL) { 6596 if (statp) 6597 free(statp); 6598 return NULL; 6599 } 6600 6601 #define MAKE_ENTRY(name) _addIntToDict(d, #name, statp->st_##name) 6602 6603 MAKE_ENTRY(mutex_align); 6604 MAKE_ENTRY(mutex_tas_spins); 6605 MAKE_ENTRY(mutex_cnt); 6606 MAKE_ENTRY(mutex_free); 6607 MAKE_ENTRY(mutex_inuse); 6608 MAKE_ENTRY(mutex_inuse_max); 6609 MAKE_ENTRY(regsize); 6610 MAKE_ENTRY(region_wait); 6611 MAKE_ENTRY(region_nowait); 6612 6613 #undef MAKE_ENTRY 6614 free(statp); 6615 return d; 6616 } 6617 #endif 6618 6619 6620 #if (DBVER >= 44) 6621 static PyObject* 6622 DBEnv_mutex_stat_print(DBEnvObject* self, PyObject* args, PyObject *kwargs) 6623 { 6624 int err; 6625 int flags=0; 6626 static char* kwnames[] = { "flags", NULL }; 6627 6628 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:mutex_stat_print", 6629 kwnames, &flags)) 6630 { 6631 return NULL; 6632 } 6633 CHECK_ENV_NOT_CLOSED(self); 6634 MYDB_BEGIN_ALLOW_THREADS; 6635 err = self->db_env->mutex_stat_print(self->db_env, flags); 6636 MYDB_END_ALLOW_THREADS; 6637 RETURN_IF_ERR(); 6638 RETURN_NONE(); 6639 } 6640 #endif 6641 6642 6643 #if (DBVER >= 43) 6644 static PyObject* 6645 DBEnv_txn_stat_print(DBEnvObject* self, PyObject* args, PyObject *kwargs) 6646 { 6647 int err; 6648 int flags=0; 6649 static char* kwnames[] = { "flags", NULL }; 6650 6651 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:stat_print", 6652 kwnames, &flags)) 6653 { 6654 return NULL; 6655 } 6656 6657 CHECK_ENV_NOT_CLOSED(self); 6658 6659 MYDB_BEGIN_ALLOW_THREADS; 6660 err = self->db_env->txn_stat_print(self->db_env, flags); 6661 MYDB_END_ALLOW_THREADS; 6662 RETURN_IF_ERR(); 6663 RETURN_NONE(); 6664 } 6665 #endif 6666 6667 4958 6668 static PyObject* 4959 6669 DBEnv_txn_stat(DBEnvObject* self, PyObject* args) … … 5048 6758 5049 6759 6760 #if (DBVER < 48) 5050 6761 static PyObject* 5051 6762 DBEnv_set_rpc_server(DBEnvObject* self, PyObject* args, PyObject* kwargs) … … 5069 6780 RETURN_NONE(); 5070 6781 } 6782 #endif 6783 6784 #if (DBVER >= 43) 6785 static PyObject* 6786 DBEnv_set_mp_max_openfd(DBEnvObject* self, PyObject* args) 6787 { 6788 int err; 6789 int maxopenfd; 6790 6791 if (!PyArg_ParseTuple(args, "i:set_mp_max_openfd", &maxopenfd)) { 6792 return NULL; 6793 } 6794 CHECK_ENV_NOT_CLOSED(self); 6795 MYDB_BEGIN_ALLOW_THREADS; 6796 err = self->db_env->set_mp_max_openfd(self->db_env, maxopenfd); 6797 MYDB_END_ALLOW_THREADS; 6798 RETURN_IF_ERR(); 6799 RETURN_NONE(); 6800 } 6801 6802 static PyObject* 6803 DBEnv_get_mp_max_openfd(DBEnvObject* self) 6804 { 6805 int err; 6806 int maxopenfd; 6807 6808 CHECK_ENV_NOT_CLOSED(self); 6809 6810 MYDB_BEGIN_ALLOW_THREADS; 6811 err = self->db_env->get_mp_max_openfd(self->db_env, &maxopenfd); 6812 MYDB_END_ALLOW_THREADS; 6813 RETURN_IF_ERR(); 6814 return NUMBER_FromLong(maxopenfd); 6815 } 6816 6817 6818 static PyObject* 6819 DBEnv_set_mp_max_write(DBEnvObject* self, PyObject* args) 6820 { 6821 int err; 6822 int maxwrite, maxwrite_sleep; 6823 6824 if (!PyArg_ParseTuple(args, "ii:set_mp_max_write", &maxwrite, 6825 &maxwrite_sleep)) { 6826 return NULL; 6827 } 6828 CHECK_ENV_NOT_CLOSED(self); 6829 MYDB_BEGIN_ALLOW_THREADS; 6830 err = self->db_env->set_mp_max_write(self->db_env, maxwrite, 6831 maxwrite_sleep); 6832 MYDB_END_ALLOW_THREADS; 6833 RETURN_IF_ERR(); 6834 RETURN_NONE(); 6835 } 6836 6837 static PyObject* 6838 DBEnv_get_mp_max_write(DBEnvObject* self) 6839 { 6840 int err; 6841 int maxwrite; 6842 #if (DBVER >= 46) 6843 db_timeout_t maxwrite_sleep; 6844 #else 6845 int maxwrite_sleep; 6846 #endif 6847 6848 CHECK_ENV_NOT_CLOSED(self); 6849 6850 MYDB_BEGIN_ALLOW_THREADS; 6851 err = self->db_env->get_mp_max_write(self->db_env, &maxwrite, 6852 &maxwrite_sleep); 6853 MYDB_END_ALLOW_THREADS; 6854 RETURN_IF_ERR(); 6855 6856 return Py_BuildValue("(ii)", maxwrite, (int)maxwrite_sleep); 6857 } 6858 #endif 6859 5071 6860 5072 6861 static PyObject* … … 5147 6936 5148 6937 if (!PyCallable_Check(notifyFunc)) { 5149 5150 6938 makeTypeError("Callable", notifyFunc); 6939 return NULL; 5151 6940 } 5152 6941 … … 5166 6955 5167 6956 if (err) { 5168 5169 6957 Py_DECREF(notifyFunc); 6958 self->event_notifyCallback = NULL; 5170 6959 } 5171 6960 … … 5488 7277 "i|O:rep_start", kwnames, &flags, &cdata_py)) 5489 7278 { 5490 7279 return NULL; 5491 7280 } 5492 7281 CHECK_ENV_NOT_CLOSED(self); … … 5626 7415 #endif 5627 7416 7417 7418 #if (DBVER >= 47) 7419 static PyObject* 7420 DBEnv_rep_set_clockskew(DBEnvObject* self, PyObject* args) 7421 { 7422 int err; 7423 unsigned int fast, slow; 7424 7425 #if (PY_VERSION_HEX >= 0x02040000) 7426 if (!PyArg_ParseTuple(args,"II:rep_set_clockskew", &fast, &slow)) 7427 return NULL; 7428 #else 7429 if (!PyArg_ParseTuple(args,"ii:rep_set_clockskew", &fast, &slow)) 7430 return NULL; 7431 #endif 7432 7433 CHECK_ENV_NOT_CLOSED(self); 7434 7435 MYDB_BEGIN_ALLOW_THREADS; 7436 err = self->db_env->rep_set_clockskew(self->db_env, fast, slow); 7437 MYDB_END_ALLOW_THREADS; 7438 RETURN_IF_ERR(); 7439 RETURN_NONE(); 7440 } 7441 7442 static PyObject* 7443 DBEnv_rep_get_clockskew(DBEnvObject* self) 7444 { 7445 int err; 7446 unsigned int fast, slow; 7447 7448 CHECK_ENV_NOT_CLOSED(self); 7449 MYDB_BEGIN_ALLOW_THREADS; 7450 err = self->db_env->rep_get_clockskew(self->db_env, &fast, &slow); 7451 MYDB_END_ALLOW_THREADS; 7452 RETURN_IF_ERR(); 7453 #if (PY_VERSION_HEX >= 0x02040000) 7454 return Py_BuildValue("(II)", fast, slow); 7455 #else 7456 return Py_BuildValue("(ii)", fast, slow); 7457 #endif 7458 } 7459 #endif 7460 7461 #if (DBVER >= 43) 7462 static PyObject* 7463 DBEnv_rep_stat_print(DBEnvObject* self, PyObject* args, PyObject *kwargs) 7464 { 7465 int err; 7466 int flags=0; 7467 static char* kwnames[] = { "flags", NULL }; 7468 7469 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:rep_stat_print", 7470 kwnames, &flags)) 7471 { 7472 return NULL; 7473 } 7474 CHECK_ENV_NOT_CLOSED(self); 7475 MYDB_BEGIN_ALLOW_THREADS; 7476 err = self->db_env->rep_stat_print(self->db_env, flags); 7477 MYDB_END_ALLOW_THREADS; 7478 RETURN_IF_ERR(); 7479 RETURN_NONE(); 7480 } 7481 #endif 7482 7483 static PyObject* 7484 DBEnv_rep_stat(DBEnvObject* self, PyObject* args, PyObject *kwargs) 7485 { 7486 int err; 7487 int flags=0; 7488 DB_REP_STAT *statp; 7489 PyObject *stats; 7490 static char* kwnames[] = { "flags", NULL }; 7491 7492 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:rep_stat", 7493 kwnames, &flags)) 7494 { 7495 return NULL; 7496 } 7497 CHECK_ENV_NOT_CLOSED(self); 7498 MYDB_BEGIN_ALLOW_THREADS; 7499 err = self->db_env->rep_stat(self->db_env, &statp, flags); 7500 MYDB_END_ALLOW_THREADS; 7501 RETURN_IF_ERR(); 7502 7503 stats=PyDict_New(); 7504 if (stats == NULL) { 7505 free(statp); 7506 return NULL; 7507 } 7508 7509 #define MAKE_ENTRY(name) _addIntToDict(stats, #name, statp->st_##name) 7510 #define MAKE_DB_LSN_ENTRY(name) _addDB_lsnToDict(stats , #name, statp->st_##name) 7511 7512 #if (DBVER >= 44) 7513 MAKE_ENTRY(bulk_fills); 7514 MAKE_ENTRY(bulk_overflows); 7515 MAKE_ENTRY(bulk_records); 7516 MAKE_ENTRY(bulk_transfers); 7517 MAKE_ENTRY(client_rerequests); 7518 MAKE_ENTRY(client_svc_miss); 7519 MAKE_ENTRY(client_svc_req); 7520 #endif 7521 MAKE_ENTRY(dupmasters); 7522 #if (DBVER >= 43) 7523 MAKE_ENTRY(egen); 7524 MAKE_ENTRY(election_nvotes); 7525 MAKE_ENTRY(startup_complete); 7526 MAKE_ENTRY(pg_duplicated); 7527 MAKE_ENTRY(pg_records); 7528 MAKE_ENTRY(pg_requested); 7529 MAKE_ENTRY(next_pg); 7530 MAKE_ENTRY(waiting_pg); 7531 #endif 7532 MAKE_ENTRY(election_cur_winner); 7533 MAKE_ENTRY(election_gen); 7534 MAKE_DB_LSN_ENTRY(election_lsn); 7535 MAKE_ENTRY(election_nsites); 7536 MAKE_ENTRY(election_priority); 7537 #if (DBVER >= 44) 7538 MAKE_ENTRY(election_sec); 7539 MAKE_ENTRY(election_usec); 7540 #endif 7541 MAKE_ENTRY(election_status); 7542 MAKE_ENTRY(election_tiebreaker); 7543 MAKE_ENTRY(election_votes); 7544 MAKE_ENTRY(elections); 7545 MAKE_ENTRY(elections_won); 7546 MAKE_ENTRY(env_id); 7547 MAKE_ENTRY(env_priority); 7548 MAKE_ENTRY(gen); 7549 MAKE_ENTRY(log_duplicated); 7550 MAKE_ENTRY(log_queued); 7551 MAKE_ENTRY(log_queued_max); 7552 MAKE_ENTRY(log_queued_total); 7553 MAKE_ENTRY(log_records); 7554 MAKE_ENTRY(log_requested); 7555 MAKE_ENTRY(master); 7556 MAKE_ENTRY(master_changes); 7557 #if (DBVER >= 47) 7558 MAKE_ENTRY(max_lease_sec); 7559 MAKE_ENTRY(max_lease_usec); 7560 MAKE_DB_LSN_ENTRY(max_perm_lsn); 7561 #endif 7562 MAKE_ENTRY(msgs_badgen); 7563 MAKE_ENTRY(msgs_processed); 7564 MAKE_ENTRY(msgs_recover); 7565 MAKE_ENTRY(msgs_send_failures); 7566 MAKE_ENTRY(msgs_sent); 7567 MAKE_ENTRY(newsites); 7568 MAKE_DB_LSN_ENTRY(next_lsn); 7569 MAKE_ENTRY(nsites); 7570 MAKE_ENTRY(nthrottles); 7571 MAKE_ENTRY(outdated); 7572 #if (DBVER >= 46) 7573 MAKE_ENTRY(startsync_delayed); 7574 #endif 7575 MAKE_ENTRY(status); 7576 MAKE_ENTRY(txns_applied); 7577 MAKE_DB_LSN_ENTRY(waiting_lsn); 7578 7579 #undef MAKE_DB_LSN_ENTRY 7580 #undef MAKE_ENTRY 7581 7582 free(statp); 7583 return stats; 7584 } 7585 5628 7586 /* --------------------------------------------------------------------- */ 5629 7587 /* REPLICATION METHODS: Replication Manager */ … … 5641 7599 "ii:repmgr_start", kwnames, &nthreads, &flags)) 5642 7600 { 5643 7601 return NULL; 5644 7602 } 5645 7603 CHECK_ENV_NOT_CLOSED(self); … … 5664 7622 "si|i:repmgr_set_local_site", kwnames, &host, &port, &flags)) 5665 7623 { 5666 7624 return NULL; 5667 7625 } 5668 7626 CHECK_ENV_NOT_CLOSED(self); … … 5688 7646 "si|i:repmgr_add_remote_site", kwnames, &host, &port, &flags)) 5689 7647 { 5690 7648 return NULL; 5691 7649 } 5692 7650 CHECK_ENV_NOT_CLOSED(self); … … 5706 7664 if (!PyArg_ParseTuple(args, "i:repmgr_set_ack_policy", &ack_policy)) 5707 7665 { 5708 7666 return NULL; 5709 7667 } 5710 7668 CHECK_ENV_NOT_CLOSED(self); … … 5881 7839 ** so nothing to do. 5882 7840 */ 5883 db->txn=NULL; 7841 db->txn=NULL; 5884 7842 } 5885 7843 } … … 5950 7908 return NULL; 5951 7909 5952 if (gid_size != DB_ XIDDATASIZE) {7910 if (gid_size != DB_GID_SIZE) { 5953 7911 PyErr_SetString(PyExc_TypeError, 5954 "gid must be DB_ XIDDATASIZE bytes long");7912 "gid must be DB_GID_SIZE bytes long"); 5955 7913 return NULL; 5956 7914 } … … 6066 8024 return NUMBER_FromLong(id); 6067 8025 } 8026 8027 8028 static PyObject* 8029 DBTxn_set_timeout(DBTxnObject* self, PyObject* args, PyObject* kwargs) 8030 { 8031 int err; 8032 u_int32_t flags=0; 8033 u_int32_t timeout = 0; 8034 static char* kwnames[] = { "timeout", "flags", NULL }; 8035 8036 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "ii:set_timeout", kwnames, 8037 &timeout, &flags)) { 8038 return NULL; 8039 } 8040 8041 MYDB_BEGIN_ALLOW_THREADS; 8042 err = self->txn->set_timeout(self->txn, (db_timeout_t)timeout, flags); 8043 MYDB_END_ALLOW_THREADS; 8044 8045 RETURN_IF_ERR(); 8046 RETURN_NONE(); 8047 } 8048 8049 8050 #if (DBVER >= 44) 8051 static PyObject* 8052 DBTxn_set_name(DBTxnObject* self, PyObject* args) 8053 { 8054 int err; 8055 const char *name; 8056 8057 if (!PyArg_ParseTuple(args, "s:set_name", &name)) 8058 return NULL; 8059 8060 MYDB_BEGIN_ALLOW_THREADS; 8061 err = self->txn->set_name(self->txn, name); 8062 MYDB_END_ALLOW_THREADS; 8063 8064 RETURN_IF_ERR(); 8065 RETURN_NONE(); 8066 } 8067 #endif 8068 8069 8070 #if (DBVER >= 44) 8071 static PyObject* 8072 DBTxn_get_name(DBTxnObject* self) 8073 { 8074 int err; 8075 const char *name; 8076 8077 MYDB_BEGIN_ALLOW_THREADS; 8078 err = self->txn->get_name(self->txn, &name); 8079 MYDB_END_ALLOW_THREADS; 8080 8081 RETURN_IF_ERR(); 8082 #if (PY_VERSION_HEX < 0x03000000) 8083 if (!name) { 8084 return PyString_FromString(""); 8085 } 8086 return PyString_FromString(name); 8087 #else 8088 if (!name) { 8089 return PyUnicode_FromString(""); 8090 } 8091 return PyUnicode_FromString(name); 8092 #endif 8093 } 8094 #endif 8095 6068 8096 6069 8097 #if (DBVER >= 43) … … 6170 8198 6171 8199 static PyObject* 6172 DBSequence_init _value(DBSequenceObject* self, PyObject* args)8200 DBSequence_initial_value(DBSequenceObject* self, PyObject* args) 6173 8201 { 6174 8202 int err; 6175 8203 PY_LONG_LONG value; 6176 8204 db_seq_t value2; 6177 if (!PyArg_ParseTuple(args,"L:init _value", &value))8205 if (!PyArg_ParseTuple(args,"L:initial_value", &value)) 6178 8206 return NULL; 6179 8207 CHECK_SEQUENCE_NOT_CLOSED(self) … … 6351 8379 max=max2; 6352 8380 return Py_BuildValue("(LL)", min, max); 8381 } 8382 8383 8384 static PyObject* 8385 DBSequence_stat_print(DBSequenceObject* self, PyObject* args, PyObject *kwargs) 8386 { 8387 int err; 8388 int flags=0; 8389 static char* kwnames[] = { "flags", NULL }; 8390 8391 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|i:stat_print", 8392 kwnames, &flags)) 8393 { 8394 return NULL; 8395 } 8396 8397 CHECK_SEQUENCE_NOT_CLOSED(self); 8398 8399 MYDB_BEGIN_ALLOW_THREADS; 8400 err = self->sequence->stat_print(self->sequence, flags); 8401 MYDB_END_ALLOW_THREADS; 8402 RETURN_IF_ERR(); 8403 RETURN_NONE(); 6353 8404 } 6354 8405 … … 6404 8455 {"associate", (PyCFunction)DB_associate, METH_VARARGS|METH_KEYWORDS}, 6405 8456 {"close", (PyCFunction)DB_close, METH_VARARGS}, 8457 #if (DBVER >= 47) 8458 {"compact", (PyCFunction)DB_compact, METH_VARARGS|METH_KEYWORDS}, 8459 #endif 6406 8460 {"consume", (PyCFunction)DB_consume, METH_VARARGS|METH_KEYWORDS}, 6407 8461 {"consume_wait", (PyCFunction)DB_consume_wait, METH_VARARGS|METH_KEYWORDS}, … … 6409 8463 {"delete", (PyCFunction)DB_delete, METH_VARARGS|METH_KEYWORDS}, 6410 8464 {"fd", (PyCFunction)DB_fd, METH_NOARGS}, 8465 #if (DBVER >= 46) 8466 {"exists", (PyCFunction)DB_exists, 8467 METH_VARARGS|METH_KEYWORDS}, 8468 #endif 6411 8469 {"get", (PyCFunction)DB_get, METH_VARARGS|METH_KEYWORDS}, 6412 8470 {"pget", (PyCFunction)DB_pget, METH_VARARGS|METH_KEYWORDS}, … … 6425 8483 {"rename", (PyCFunction)DB_rename, METH_VARARGS}, 6426 8484 {"set_bt_minkey", (PyCFunction)DB_set_bt_minkey, METH_VARARGS}, 8485 #if (DBVER >= 42) 8486 {"get_bt_minkey", (PyCFunction)DB_get_bt_minkey, METH_NOARGS}, 8487 #endif 6427 8488 {"set_bt_compare", (PyCFunction)DB_set_bt_compare, METH_O}, 6428 8489 {"set_cachesize", (PyCFunction)DB_set_cachesize, METH_VARARGS}, 6429 #if (DBVER >= 41) 8490 #if (DBVER >= 42) 8491 {"get_cachesize", (PyCFunction)DB_get_cachesize, METH_NOARGS}, 8492 #endif 6430 8493 {"set_encrypt", (PyCFunction)DB_set_encrypt, METH_VARARGS|METH_KEYWORDS}, 6431 #endif 8494 #if (DBVER >= 42) 8495 {"get_encrypt_flags", (PyCFunction)DB_get_encrypt_flags, METH_NOARGS}, 8496 #endif 8497 6432 8498 {"set_flags", (PyCFunction)DB_set_flags, METH_VARARGS}, 8499 #if (DBVER >= 42) 8500 {"get_flags", (PyCFunction)DB_get_flags, METH_NOARGS}, 8501 #endif 6433 8502 {"set_h_ffactor", (PyCFunction)DB_set_h_ffactor, METH_VARARGS}, 8503 #if (DBVER >= 42) 8504 {"get_h_ffactor", (PyCFunction)DB_get_h_ffactor, METH_NOARGS}, 8505 #endif 6434 8506 {"set_h_nelem", (PyCFunction)DB_set_h_nelem, METH_VARARGS}, 8507 #if (DBVER >= 42) 8508 {"get_h_nelem", (PyCFunction)DB_get_h_nelem, METH_NOARGS}, 8509 #endif 6435 8510 {"set_lorder", (PyCFunction)DB_set_lorder, METH_VARARGS}, 8511 #if (DBVER >= 42) 8512 {"get_lorder", (PyCFunction)DB_get_lorder, METH_NOARGS}, 8513 #endif 6436 8514 {"set_pagesize", (PyCFunction)DB_set_pagesize, METH_VARARGS}, 8515 #if (DBVER >= 42) 8516 {"get_pagesize", (PyCFunction)DB_get_pagesize, METH_NOARGS}, 8517 #endif 6437 8518 {"set_re_delim", (PyCFunction)DB_set_re_delim, METH_VARARGS}, 8519 #if (DBVER >= 42) 8520 {"get_re_delim", (PyCFunction)DB_get_re_delim, METH_NOARGS}, 8521 #endif 6438 8522 {"set_re_len", (PyCFunction)DB_set_re_len, METH_VARARGS}, 8523 #if (DBVER >= 42) 8524 {"get_re_len", (PyCFunction)DB_get_re_len, METH_NOARGS}, 8525 #endif 6439 8526 {"set_re_pad", (PyCFunction)DB_set_re_pad, METH_VARARGS}, 8527 #if (DBVER >= 42) 8528 {"get_re_pad", (PyCFunction)DB_get_re_pad, METH_NOARGS}, 8529 #endif 6440 8530 {"set_re_source", (PyCFunction)DB_set_re_source, METH_VARARGS}, 8531 #if (DBVER >= 42) 8532 {"get_re_source", (PyCFunction)DB_get_re_source, METH_NOARGS}, 8533 #endif 6441 8534 {"set_q_extentsize",(PyCFunction)DB_set_q_extentsize, METH_VARARGS}, 8535 #if (DBVER >= 42) 8536 {"get_q_extentsize",(PyCFunction)DB_get_q_extentsize, METH_NOARGS}, 8537 #endif 6442 8538 {"set_private", (PyCFunction)DB_set_private, METH_O}, 6443 8539 {"get_private", (PyCFunction)DB_get_private, METH_NOARGS}, 8540 #if (DBVER >= 46) 8541 {"set_priority", (PyCFunction)DB_set_priority, METH_VARARGS}, 8542 {"get_priority", (PyCFunction)DB_get_priority, METH_NOARGS}, 8543 #endif 6444 8544 {"stat", (PyCFunction)DB_stat, METH_VARARGS|METH_KEYWORDS}, 8545 #if (DBVER >= 43) 8546 {"stat_print", (PyCFunction)DB_stat_print, 8547 METH_VARARGS|METH_KEYWORDS}, 8548 #endif 6445 8549 {"sync", (PyCFunction)DB_sync, METH_VARARGS}, 6446 8550 {"truncate", (PyCFunction)DB_truncate, METH_VARARGS|METH_KEYWORDS}, … … 6453 8557 }; 6454 8558 8559 8560 /* We need this to support __contains__() */ 8561 static PySequenceMethods DB_sequence = { 8562 0, /* sq_length, mapping wins here */ 8563 0, /* sq_concat */ 8564 0, /* sq_repeat */ 8565 0, /* sq_item */ 8566 0, /* sq_slice */ 8567 0, /* sq_ass_item */ 8568 0, /* sq_ass_slice */ 8569 (objobjproc)DB_contains, /* sq_contains */ 8570 0, /* sq_inplace_concat */ 8571 0, /* sq_inplace_repeat */ 8572 }; 6455 8573 6456 8574 static PyMappingMethods DB_mapping = { … … 6484 8602 {"next_dup", (PyCFunction)DBC_next_dup, METH_VARARGS|METH_KEYWORDS}, 6485 8603 {"next_nodup", (PyCFunction)DBC_next_nodup, METH_VARARGS|METH_KEYWORDS}, 8604 #if (DBVER >= 46) 8605 {"prev_dup", (PyCFunction)DBC_prev_dup, 8606 METH_VARARGS|METH_KEYWORDS}, 8607 #endif 6486 8608 {"prev_nodup", (PyCFunction)DBC_prev_nodup, METH_VARARGS|METH_KEYWORDS}, 6487 8609 {"join_item", (PyCFunction)DBC_join_item, METH_VARARGS}, 8610 #if (DBVER >= 46) 8611 {"set_priority", (PyCFunction)DBC_set_priority, 8612 METH_VARARGS|METH_KEYWORDS}, 8613 {"get_priority", (PyCFunction)DBC_get_priority, METH_NOARGS}, 8614 #endif 8615 {NULL, NULL} /* sentinel */ 8616 }; 8617 8618 8619 static PyMethodDef DBLogCursor_methods[] = { 8620 {"close", (PyCFunction)DBLogCursor_close, METH_NOARGS}, 8621 {"current", (PyCFunction)DBLogCursor_current, METH_NOARGS}, 8622 {"first", (PyCFunction)DBLogCursor_first, METH_NOARGS}, 8623 {"last", (PyCFunction)DBLogCursor_last, METH_NOARGS}, 8624 {"next", (PyCFunction)DBLogCursor_next, METH_NOARGS}, 8625 {"prev", (PyCFunction)DBLogCursor_prev, METH_NOARGS}, 8626 {"set", (PyCFunction)DBLogCursor_set, METH_VARARGS}, 6488 8627 {NULL, NULL} /* sentinel */ 6489 8628 }; … … 6494 8633 {"open", (PyCFunction)DBEnv_open, METH_VARARGS}, 6495 8634 {"remove", (PyCFunction)DBEnv_remove, METH_VARARGS}, 6496 #if (DBVER >= 41)6497 8635 {"dbremove", (PyCFunction)DBEnv_dbremove, METH_VARARGS|METH_KEYWORDS}, 6498 8636 {"dbrename", (PyCFunction)DBEnv_dbrename, METH_VARARGS|METH_KEYWORDS}, 8637 #if (DBVER >= 46) 8638 {"set_thread_count", (PyCFunction)DBEnv_set_thread_count, METH_VARARGS}, 8639 {"get_thread_count", (PyCFunction)DBEnv_get_thread_count, METH_NOARGS}, 8640 #endif 6499 8641 {"set_encrypt", (PyCFunction)DBEnv_set_encrypt, METH_VARARGS|METH_KEYWORDS}, 6500 #endif 6501 {"set_timeout", (PyCFunction)DBEnv_set_timeout, METH_VARARGS|METH_KEYWORDS}, 6502 {"set_shm_key", (PyCFunction)DBEnv_set_shm_key, METH_VARARGS}, 6503 {"set_cachesize", (PyCFunction)DBEnv_set_cachesize, METH_VARARGS}, 6504 {"set_data_dir", (PyCFunction)DBEnv_set_data_dir, METH_VARARGS}, 6505 {"set_flags", (PyCFunction)DBEnv_set_flags, METH_VARARGS}, 8642 #if (DBVER >= 42) 8643 {"get_encrypt_flags", (PyCFunction)DBEnv_get_encrypt_flags, METH_NOARGS}, 8644 {"get_timeout", (PyCFunction)DBEnv_get_timeout, 8645 METH_VARARGS|METH_KEYWORDS}, 8646 #endif 8647 {"set_timeout", (PyCFunction)DBEnv_set_timeout, METH_VARARGS|METH_KEYWORDS}, 8648 {"set_shm_key", (PyCFunction)DBEnv_set_shm_key, METH_VARARGS}, 8649 #if (DBVER >= 42) 8650 {"get_shm_key", (PyCFunction)DBEnv_get_shm_key, METH_NOARGS}, 8651 #endif 8652 #if (DBVER >= 46) 8653 {"set_cache_max", (PyCFunction)DBEnv_set_cache_max, METH_VARARGS}, 8654 {"get_cache_max", (PyCFunction)DBEnv_get_cache_max, METH_NOARGS}, 8655 #endif 8656 {"set_cachesize", (PyCFunction)DBEnv_set_cachesize, METH_VARARGS}, 8657 #if (DBVER >= 42) 8658 {"get_cachesize", (PyCFunction)DBEnv_get_cachesize, METH_NOARGS}, 8659 #endif 8660 {"memp_trickle", (PyCFunction)DBEnv_memp_trickle, METH_VARARGS}, 8661 {"memp_sync", (PyCFunction)DBEnv_memp_sync, METH_VARARGS}, 8662 {"memp_stat", (PyCFunction)DBEnv_memp_stat, 8663 METH_VARARGS|METH_KEYWORDS}, 8664 #if (DBVER >= 43) 8665 {"memp_stat_print", (PyCFunction)DBEnv_memp_stat_print, 8666 METH_VARARGS|METH_KEYWORDS}, 8667 #endif 8668 #if (DBVER >= 44) 8669 {"mutex_set_max", (PyCFunction)DBEnv_mutex_set_max, METH_VARARGS}, 8670 {"mutex_get_max", (PyCFunction)DBEnv_mutex_get_max, METH_NOARGS}, 8671 {"mutex_set_align", (PyCFunction)DBEnv_mutex_set_align, METH_VARARGS}, 8672 {"mutex_get_align", (PyCFunction)DBEnv_mutex_get_align, METH_NOARGS}, 8673 {"mutex_set_increment", (PyCFunction)DBEnv_mutex_set_increment, 8674 METH_VARARGS}, 8675 {"mutex_get_increment", (PyCFunction)DBEnv_mutex_get_increment, 8676 METH_NOARGS}, 8677 {"mutex_set_tas_spins", (PyCFunction)DBEnv_mutex_set_tas_spins, 8678 METH_VARARGS}, 8679 {"mutex_get_tas_spins", (PyCFunction)DBEnv_mutex_get_tas_spins, 8680 METH_NOARGS}, 8681 {"mutex_stat", (PyCFunction)DBEnv_mutex_stat, METH_VARARGS}, 8682 #if (DBVER >= 44) 8683 {"mutex_stat_print", (PyCFunction)DBEnv_mutex_stat_print, 8684 METH_VARARGS|METH_KEYWORDS}, 8685 #endif 8686 #endif 8687 {"set_data_dir", (PyCFunction)DBEnv_set_data_dir, METH_VARARGS}, 8688 #if (DBVER >= 42) 8689 {"get_data_dirs", (PyCFunction)DBEnv_get_data_dirs, METH_NOARGS}, 8690 #endif 8691 #if (DBVER >= 42) 8692 {"get_flags", (PyCFunction)DBEnv_get_flags, METH_NOARGS}, 8693 #endif 8694 {"set_flags", (PyCFunction)DBEnv_set_flags, METH_VARARGS}, 6506 8695 #if (DBVER >= 47) 6507 {"log_set_config", (PyCFunction)DBEnv_log_set_config, METH_VARARGS}, 6508 #endif 6509 {"set_lg_bsize", (PyCFunction)DBEnv_set_lg_bsize, METH_VARARGS}, 6510 {"set_lg_dir", (PyCFunction)DBEnv_set_lg_dir, METH_VARARGS}, 6511 {"set_lg_max", (PyCFunction)DBEnv_set_lg_max, METH_VARARGS}, 8696 {"log_set_config", (PyCFunction)DBEnv_log_set_config, METH_VARARGS}, 8697 {"log_get_config", (PyCFunction)DBEnv_log_get_config, METH_VARARGS}, 8698 #endif 8699 {"set_lg_bsize", (PyCFunction)DBEnv_set_lg_bsize, METH_VARARGS}, 6512 8700 #if (DBVER >= 42) 6513 {"get_lg_max", (PyCFunction)DBEnv_get_lg_max, METH_NOARGS}, 8701 {"get_lg_bsize", (PyCFunction)DBEnv_get_lg_bsize, METH_NOARGS}, 8702 #endif 8703 {"set_lg_dir", (PyCFunction)DBEnv_set_lg_dir, METH_VARARGS}, 8704 #if (DBVER >= 42) 8705 {"get_lg_dir", (PyCFunction)DBEnv_get_lg_dir, METH_NOARGS}, 8706 #endif 8707 {"set_lg_max", (PyCFunction)DBEnv_set_lg_max, METH_VARARGS}, 8708 #if (DBVER >= 42) 8709 {"get_lg_max", (PyCFunction)DBEnv_get_lg_max, METH_NOARGS}, 6514 8710 #endif 6515 8711 {"set_lg_regionmax",(PyCFunction)DBEnv_set_lg_regionmax, METH_VARARGS}, 6516 {"set_lk_detect", (PyCFunction)DBEnv_set_lk_detect, METH_VARARGS}, 8712 #if (DBVER >= 42) 8713 {"get_lg_regionmax",(PyCFunction)DBEnv_get_lg_regionmax, METH_NOARGS}, 8714 #endif 8715 #if (DBVER >= 44) 8716 {"set_lg_filemode", (PyCFunction)DBEnv_set_lg_filemode, METH_VARARGS}, 8717 {"get_lg_filemode", (PyCFunction)DBEnv_get_lg_filemode, METH_NOARGS}, 8718 #endif 8719 #if (DBVER >= 47) 8720 {"set_lk_partitions", (PyCFunction)DBEnv_set_lk_partitions, METH_VARARGS}, 8721 {"get_lk_partitions", (PyCFunction)DBEnv_get_lk_partitions, METH_NOARGS}, 8722 #endif 8723 {"set_lk_detect", (PyCFunction)DBEnv_set_lk_detect, METH_VARARGS}, 8724 #if (DBVER >= 42) 8725 {"get_lk_detect", (PyCFunction)DBEnv_get_lk_detect, METH_NOARGS}, 8726 #endif 6517 8727 #if (DBVER < 45) 6518 {"set_lk_max", (PyCFunction)DBEnv_set_lk_max, 8728 {"set_lk_max", (PyCFunction)DBEnv_set_lk_max, METH_VARARGS}, 6519 8729 #endif 6520 8730 {"set_lk_max_locks", (PyCFunction)DBEnv_set_lk_max_locks, METH_VARARGS}, 8731 #if (DBVER >= 42) 8732 {"get_lk_max_locks", (PyCFunction)DBEnv_get_lk_max_locks, METH_NOARGS}, 8733 #endif 6521 8734 {"set_lk_max_lockers", (PyCFunction)DBEnv_set_lk_max_lockers, METH_VARARGS}, 8735 #if (DBVER >= 42) 8736 {"get_lk_max_lockers", (PyCFunction)DBEnv_get_lk_max_lockers, METH_NOARGS}, 8737 #endif 6522 8738 {"set_lk_max_objects", (PyCFunction)DBEnv_set_lk_max_objects, METH_VARARGS}, 6523 {"set_mp_mmapsize", (PyCFunction)DBEnv_set_mp_mmapsize, METH_VARARGS}, 6524 {"set_tmp_dir", (PyCFunction)DBEnv_set_tmp_dir, METH_VARARGS}, 6525 {"txn_begin", (PyCFunction)DBEnv_txn_begin, METH_VARARGS|METH_KEYWORDS}, 6526 {"txn_checkpoint", (PyCFunction)DBEnv_txn_checkpoint, METH_VARARGS}, 6527 {"txn_stat", (PyCFunction)DBEnv_txn_stat, METH_VARARGS}, 6528 {"set_tx_max", (PyCFunction)DBEnv_set_tx_max, METH_VARARGS}, 8739 #if (DBVER >= 42) 8740 {"get_lk_max_objects", (PyCFunction)DBEnv_get_lk_max_objects, METH_NOARGS}, 8741 #endif 8742 #if (DBVER >= 43) 8743 {"stat_print", (PyCFunction)DBEnv_stat_print, 8744 METH_VARARGS|METH_KEYWORDS}, 8745 #endif 8746 {"set_mp_mmapsize", (PyCFunction)DBEnv_set_mp_mmapsize, METH_VARARGS}, 8747 #if (DBVER >= 42) 8748 {"get_mp_mmapsize", (PyCFunction)DBEnv_get_mp_mmapsize, METH_NOARGS}, 8749 #endif 8750 {"set_tmp_dir", (PyCFunction)DBEnv_set_tmp_dir, METH_VARARGS}, 8751 #if (DBVER >= 42) 8752 {"get_tmp_dir", (PyCFunction)DBEnv_get_tmp_dir, METH_NOARGS}, 8753 #endif 8754 {"txn_begin", (PyCFunction)DBEnv_txn_begin, METH_VARARGS|METH_KEYWORDS}, 8755 {"txn_checkpoint", (PyCFunction)DBEnv_txn_checkpoint, METH_VARARGS}, 8756 {"txn_stat", (PyCFunction)DBEnv_txn_stat, METH_VARARGS}, 8757 #if (DBVER >= 43) 8758 {"txn_stat_print", (PyCFunction)DBEnv_txn_stat_print, 8759 METH_VARARGS|METH_KEYWORDS}, 8760 #endif 8761 #if (DBVER >= 42) 8762 {"get_tx_max", (PyCFunction)DBEnv_get_tx_max, METH_NOARGS}, 8763 {"get_tx_timestamp", (PyCFunction)DBEnv_get_tx_timestamp, METH_NOARGS}, 8764 #endif 8765 {"set_tx_max", (PyCFunction)DBEnv_set_tx_max, METH_VARARGS}, 6529 8766 {"set_tx_timestamp", (PyCFunction)DBEnv_set_tx_timestamp, METH_VARARGS}, 6530 {"lock_detect", (PyCFunction)DBEnv_lock_detect, METH_VARARGS}, 6531 {"lock_get", (PyCFunction)DBEnv_lock_get, METH_VARARGS}, 6532 {"lock_id", (PyCFunction)DBEnv_lock_id, METH_NOARGS}, 6533 {"lock_id_free", (PyCFunction)DBEnv_lock_id_free, METH_VARARGS}, 6534 {"lock_put", (PyCFunction)DBEnv_lock_put, METH_VARARGS}, 6535 {"lock_stat", (PyCFunction)DBEnv_lock_stat, METH_VARARGS}, 6536 {"log_archive", (PyCFunction)DBEnv_log_archive, METH_VARARGS}, 6537 {"log_flush", (PyCFunction)DBEnv_log_flush, METH_NOARGS}, 6538 {"log_stat", (PyCFunction)DBEnv_log_stat, METH_VARARGS}, 8767 {"lock_detect", (PyCFunction)DBEnv_lock_detect, METH_VARARGS}, 8768 {"lock_get", (PyCFunction)DBEnv_lock_get, METH_VARARGS}, 8769 {"lock_id", (PyCFunction)DBEnv_lock_id, METH_NOARGS}, 8770 {"lock_id_free", (PyCFunction)DBEnv_lock_id_free, METH_VARARGS}, 8771 {"lock_put", (PyCFunction)DBEnv_lock_put, METH_VARARGS}, 8772 {"lock_stat", (PyCFunction)DBEnv_lock_stat, METH_VARARGS}, 8773 #if (DBVER >= 43) 8774 {"lock_stat_print", (PyCFunction)DBEnv_lock_stat_print, 8775 METH_VARARGS|METH_KEYWORDS}, 8776 #endif 8777 {"log_cursor", (PyCFunction)DBEnv_log_cursor, METH_NOARGS}, 8778 {"log_file", (PyCFunction)DBEnv_log_file, METH_VARARGS}, 6539 8779 #if (DBVER >= 44) 6540 {"lsn_reset", (PyCFunction)DBEnv_lsn_reset, METH_VARARGS|METH_KEYWORDS}, 8780 {"log_printf", (PyCFunction)DBEnv_log_printf, 8781 METH_VARARGS|METH_KEYWORDS}, 8782 #endif 8783 {"log_archive", (PyCFunction)DBEnv_log_archive, METH_VARARGS}, 8784 {"log_flush", (PyCFunction)DBEnv_log_flush, METH_NOARGS}, 8785 {"log_stat", (PyCFunction)DBEnv_log_stat, METH_VARARGS}, 8786 #if (DBVER >= 43) 8787 {"log_stat_print", (PyCFunction)DBEnv_log_stat_print, 8788 METH_VARARGS|METH_KEYWORDS}, 8789 #endif 8790 #if (DBVER >= 44) 8791 {"fileid_reset", (PyCFunction)DBEnv_fileid_reset, METH_VARARGS|METH_KEYWORDS}, 8792 {"lsn_reset", (PyCFunction)DBEnv_lsn_reset, METH_VARARGS|METH_KEYWORDS}, 6541 8793 #endif 6542 8794 {"set_get_returns_none",(PyCFunction)DBEnv_set_get_returns_none, METH_VARARGS}, 6543 {"txn_recover", (PyCFunction)DBEnv_txn_recover, METH_NOARGS}, 8795 {"txn_recover", (PyCFunction)DBEnv_txn_recover, METH_NOARGS}, 8796 #if (DBVER < 48) 6544 8797 {"set_rpc_server", (PyCFunction)DBEnv_set_rpc_server, 6545 8798 METH_VARARGS||METH_KEYWORDS}, 6546 {"set_verbose", (PyCFunction)DBEnv_set_verbose, METH_VARARGS}, 8799 #endif 8800 #if (DBVER >= 43) 8801 {"set_mp_max_openfd", (PyCFunction)DBEnv_set_mp_max_openfd, METH_VARARGS}, 8802 {"get_mp_max_openfd", (PyCFunction)DBEnv_get_mp_max_openfd, METH_NOARGS}, 8803 {"set_mp_max_write", (PyCFunction)DBEnv_set_mp_max_write, METH_VARARGS}, 8804 {"get_mp_max_write", (PyCFunction)DBEnv_get_mp_max_write, METH_NOARGS}, 8805 #endif 8806 {"set_verbose", (PyCFunction)DBEnv_set_verbose, METH_VARARGS}, 6547 8807 #if (DBVER >= 42) 6548 8808 {"get_verbose", (PyCFunction)DBEnv_get_verbose, METH_VARARGS}, … … 6582 8842 {"rep_get_timeout", (PyCFunction)DBEnv_rep_get_timeout, METH_VARARGS}, 6583 8843 #endif 8844 #if (DBVER >= 47) 8845 {"rep_set_clockskew", (PyCFunction)DBEnv_rep_set_clockskew, METH_VARARGS}, 8846 {"rep_get_clockskew", (PyCFunction)DBEnv_rep_get_clockskew, METH_VARARGS}, 8847 #endif 8848 {"rep_stat", (PyCFunction)DBEnv_rep_stat, 8849 METH_VARARGS|METH_KEYWORDS}, 8850 #if (DBVER >= 43) 8851 {"rep_stat_print", (PyCFunction)DBEnv_rep_stat_print, 8852 METH_VARARGS|METH_KEYWORDS}, 8853 #endif 8854 6584 8855 #if (DBVER >= 45) 6585 8856 {"repmgr_start", (PyCFunction)DBEnv_repmgr_start, … … 6612 8883 {"abort", (PyCFunction)DBTxn_abort, METH_NOARGS}, 6613 8884 {"id", (PyCFunction)DBTxn_id, METH_NOARGS}, 8885 {"set_timeout", (PyCFunction)DBTxn_set_timeout, 8886 METH_VARARGS|METH_KEYWORDS}, 8887 #if (DBVER >= 44) 8888 {"set_name", (PyCFunction)DBTxn_set_name, METH_VARARGS}, 8889 {"get_name", (PyCFunction)DBTxn_get_name, METH_NOARGS}, 8890 #endif 6614 8891 {NULL, NULL} /* sentinel */ 6615 8892 }; … … 6622 8899 {"get_dbp", (PyCFunction)DBSequence_get_dbp, METH_NOARGS}, 6623 8900 {"get_key", (PyCFunction)DBSequence_get_key, METH_NOARGS}, 6624 {"init _value", (PyCFunction)DBSequence_init_value,METH_VARARGS},8901 {"initial_value", (PyCFunction)DBSequence_initial_value, METH_VARARGS}, 6625 8902 {"open", (PyCFunction)DBSequence_open, METH_VARARGS|METH_KEYWORDS}, 6626 8903 {"remove", (PyCFunction)DBSequence_remove, METH_VARARGS|METH_KEYWORDS}, … … 6632 8909 {"get_range", (PyCFunction)DBSequence_get_range, METH_NOARGS}, 6633 8910 {"stat", (PyCFunction)DBSequence_stat, METH_VARARGS|METH_KEYWORDS}, 8911 {"stat_print", (PyCFunction)DBSequence_stat_print, 8912 METH_VARARGS|METH_KEYWORDS}, 6634 8913 {NULL, NULL} /* sentinel */ 6635 8914 }; … … 6645 8924 6646 8925 #if (DBVER >= 42) 8926 MYDB_BEGIN_ALLOW_THREADS; 6647 8927 self->db_env->get_home(self->db_env, &home); 8928 MYDB_END_ALLOW_THREADS; 6648 8929 #else 6649 8930 home=self->db_env->db_home; … … 6680 8961 0, /*tp_repr*/ 6681 8962 0, /*tp_as_number*/ 6682 0,/*tp_as_sequence*/8963 &DB_sequence,/*tp_as_sequence*/ 6683 8964 &DB_mapping,/*tp_as_mapping*/ 6684 8965 0, /*tp_hash*/ 6685 0, 6686 0, 6687 0, 8966 0, /* tp_call */ 8967 0, /* tp_str */ 8968 0, /* tp_getattro */ 6688 8969 0, /* tp_setattro */ 6689 0, 8970 0, /* tp_as_buffer */ 6690 8971 #if (PY_VERSION_HEX < 0x03000000) 6691 8972 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_WEAKREFS, /* tp_flags */ … … 6694 8975 #endif 6695 8976 0, /* tp_doc */ 6696 0, 6697 0, 6698 0, 8977 0, /* tp_traverse */ 8978 0, /* tp_clear */ 8979 0, /* tp_richcompare */ 6699 8980 offsetof(DBObject, in_weakreflist), /* tp_weaklistoffset */ 6700 8981 0, /*tp_iter*/ … … 6748 9029 6749 9030 9031 statichere PyTypeObject DBLogCursor_Type = { 9032 #if (PY_VERSION_HEX < 0x03000000) 9033 PyObject_HEAD_INIT(NULL) 9034 0, /*ob_size*/ 9035 #else 9036 PyVarObject_HEAD_INIT(NULL, 0) 9037 #endif 9038 "DBLogCursor", /*tp_name*/ 9039 sizeof(DBLogCursorObject), /*tp_basicsize*/ 9040 0, /*tp_itemsize*/ 9041 /* methods */ 9042 (destructor)DBLogCursor_dealloc,/*tp_dealloc*/ 9043 0, /*tp_print*/ 9044 0, /*tp_getattr*/ 9045 0, /*tp_setattr*/ 9046 0, /*tp_compare*/ 9047 0, /*tp_repr*/ 9048 0, /*tp_as_number*/ 9049 0, /*tp_as_sequence*/ 9050 0, /*tp_as_mapping*/ 9051 0, /*tp_hash*/ 9052 0, /*tp_call*/ 9053 0, /*tp_str*/ 9054 0, /*tp_getattro*/ 9055 0, /*tp_setattro*/ 9056 0, /*tp_as_buffer*/ 9057 #if (PY_VERSION_HEX < 0x03000000) 9058 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_WEAKREFS, /* tp_flags */ 9059 #else 9060 Py_TPFLAGS_DEFAULT, /* tp_flags */ 9061 #endif 9062 0, /* tp_doc */ 9063 0, /* tp_traverse */ 9064 0, /* tp_clear */ 9065 0, /* tp_richcompare */ 9066 offsetof(DBLogCursorObject, in_weakreflist), /* tp_weaklistoffset */ 9067 0, /*tp_iter*/ 9068 0, /*tp_iternext*/ 9069 DBLogCursor_methods, /*tp_methods*/ 9070 0, /*tp_members*/ 9071 }; 9072 9073 6750 9074 statichere PyTypeObject DBEnv_Type = { 6751 9075 #if (PY_VERSION_HEX < 0x03000000) … … 6769 9093 0, /*tp_as_mapping*/ 6770 9094 0, /*tp_hash*/ 6771 0, 6772 0, 6773 0, 9095 0, /* tp_call */ 9096 0, /* tp_str */ 9097 0, /* tp_getattro */ 6774 9098 0, /* tp_setattro */ 6775 0, 9099 0, /* tp_as_buffer */ 6776 9100 #if (PY_VERSION_HEX < 0x03000000) 6777 9101 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_WEAKREFS, /* tp_flags */ … … 6780 9104 #endif 6781 9105 0, /* tp_doc */ 6782 0, 6783 0, 6784 0, 9106 0, /* tp_traverse */ 9107 0, /* tp_clear */ 9108 0, /* tp_richcompare */ 6785 9109 offsetof(DBEnvObject, in_weakreflist), /* tp_weaklistoffset */ 6786 9110 0, /* tp_iter */ … … 6812 9136 0, /*tp_as_mapping*/ 6813 9137 0, /*tp_hash*/ 6814 0, 6815 0, 6816 0, 9138 0, /* tp_call */ 9139 0, /* tp_str */ 9140 0, /* tp_getattro */ 6817 9141 0, /* tp_setattro */ 6818 0, 9142 0, /* tp_as_buffer */ 6819 9143 #if (PY_VERSION_HEX < 0x03000000) 6820 9144 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_WEAKREFS, /* tp_flags */ … … 6823 9147 #endif 6824 9148 0, /* tp_doc */ 6825 0, 6826 0, 6827 0, 9149 0, /* tp_traverse */ 9150 0, /* tp_clear */ 9151 0, /* tp_richcompare */ 6828 9152 offsetof(DBTxnObject, in_weakreflist), /* tp_weaklistoffset */ 6829 9153 0, /*tp_iter*/ … … 6855 9179 0, /*tp_as_mapping*/ 6856 9180 0, /*tp_hash*/ 6857 0, 6858 0, 6859 0, 9181 0, /* tp_call */ 9182 0, /* tp_str */ 9183 0, /* tp_getattro */ 6860 9184 0, /* tp_setattro */ 6861 0, 9185 0, /* tp_as_buffer */ 6862 9186 #if (PY_VERSION_HEX < 0x03000000) 6863 9187 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_WEAKREFS, /* tp_flags */ … … 6866 9190 #endif 6867 9191 0, /* tp_doc */ 6868 0, 6869 0, 6870 0, 9192 0, /* tp_traverse */ 9193 0, /* tp_clear */ 9194 0, /* tp_richcompare */ 6871 9195 offsetof(DBLockObject, in_weakreflist), /* tp_weaklistoffset */ 6872 9196 }; … … 6894 9218 0, /*tp_as_mapping*/ 6895 9219 0, /*tp_hash*/ 6896 0, 6897 0, 6898 0, 9220 0, /* tp_call */ 9221 0, /* tp_str */ 9222 0, /* tp_getattro */ 6899 9223 0, /* tp_setattro */ 6900 0, 9224 0, /* tp_as_buffer */ 6901 9225 #if (PY_VERSION_HEX < 0x03000000) 6902 9226 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_WEAKREFS, /* tp_flags */ … … 6905 9229 #endif 6906 9230 0, /* tp_doc */ 6907 0, 6908 0, 6909 0, 9231 0, /* tp_traverse */ 9232 0, /* tp_clear */ 9233 0, /* tp_richcompare */ 6910 9234 offsetof(DBSequenceObject, in_weakreflist), /* tp_weaklistoffset */ 6911 9235 0, /*tp_iter*/ … … 7032 9356 PyObject* m; 7033 9357 PyObject* d; 7034 PyObject* pybsddb_version_s = PyBytes_FromString( PY_BSDDB_VERSION );7035 PyObject* db_version_s = PyBytes_FromString( DB_VERSION_STRING );7036 PyObject* cvsid_s = PyBytes_FromString( rcs_id );7037 9358 PyObject* py_api; 9359 PyObject* pybsddb_version_s; 9360 PyObject* db_version_s; 9361 PyObject* cvsid_s; 9362 9363 #if (PY_VERSION_HEX < 0x03000000) 9364 pybsddb_version_s = PyString_FromString(PY_BSDDB_VERSION); 9365 db_version_s = PyString_FromString(DB_VERSION_STRING); 9366 cvsid_s = PyString_FromString(rcs_id); 9367 #else 9368 /* This data should be ascii, so UTF-8 conversion is fine */ 9369 pybsddb_version_s = PyUnicode_FromString(PY_BSDDB_VERSION); 9370 db_version_s = PyUnicode_FromString(DB_VERSION_STRING); 9371 cvsid_s = PyUnicode_FromString(rcs_id); 9372 #endif 7038 9373 7039 9374 /* Initialize object types */ 7040 9375 if ((PyType_Ready(&DB_Type) < 0) 7041 9376 || (PyType_Ready(&DBCursor_Type) < 0) 9377 || (PyType_Ready(&DBLogCursor_Type) < 0) 7042 9378 || (PyType_Ready(&DBEnv_Type) < 0) 7043 9379 || (PyType_Ready(&DBTxn_Type) < 0) … … 7069 9405 return; 7070 9406 #else 7071 9407 return NULL; 7072 9408 #endif 7073 9409 } … … 7092 9428 ADD_INT(d, DB_MAX_RECORDS); 7093 9429 9430 #if (DBVER < 48) 7094 9431 #if (DBVER >= 42) 7095 9432 ADD_INT(d, DB_RPCCLIENT); … … 7099 9436 _addIntToDict(d, "DB_RPCCLIENT", DB_CLIENT); 7100 9437 #endif 9438 #endif 9439 9440 #if (DBVER < 48) 7101 9441 ADD_INT(d, DB_XA_CREATE); 9442 #endif 7102 9443 7103 9444 ADD_INT(d, DB_CREATE); … … 7116 9457 ADD_INT(d, DB_JOINENV); 7117 9458 9459 #if (DBVER >= 48) 9460 ADD_INT(d, DB_GID_SIZE); 9461 #else 7118 9462 ADD_INT(d, DB_XIDDATASIZE); 9463 /* Allow new code to work in old BDB releases */ 9464 _addIntToDict(d, "DB_GID_SIZE", DB_XIDDATASIZE); 9465 #endif 7119 9466 7120 9467 ADD_INT(d, DB_RECOVER); … … 7130 9477 ADD_INT(d, DB_TXN_SYNC); 7131 9478 ADD_INT(d, DB_TXN_NOWAIT); 9479 9480 #if (DBVER >= 46) 9481 ADD_INT(d, DB_TXN_WAIT); 9482 #endif 7132 9483 7133 9484 ADD_INT(d, DB_EXCL); … … 7142 9493 ADD_INT(d, DB_UPGRADE); 7143 9494 9495 ADD_INT(d, DB_PRINTABLE); 7144 9496 ADD_INT(d, DB_AGGRESSIVE); 7145 9497 ADD_INT(d, DB_NOORDERCHK); … … 7227 9579 ADD_INT(d, DB_SNAPSHOT); 7228 9580 9581 #if (DBVER >= 43) 9582 ADD_INT(d, DB_INORDER); 9583 #endif 9584 7229 9585 ADD_INT(d, DB_JOIN_NOSORT); 7230 9586 … … 7236 9592 #endif 7237 9593 7238 #if (DBVER >= 41)7239 _addIntToDict(d, "DB_CHECKPOINT", 0);7240 #else7241 ADD_INT(d, DB_CHECKPOINT);7242 ADD_INT(d, DB_CURLSN);7243 #endif7244 9594 #if (DBVER <= 41) 7245 9595 ADD_INT(d, DB_COMMIT); … … 7252 9602 ADD_INT(d, DB_FLUSH); 7253 9603 ADD_INT(d, DB_GET_BOTH); 9604 ADD_INT(d, DB_GET_BOTH_RANGE); 7254 9605 ADD_INT(d, DB_GET_RECNO); 7255 9606 ADD_INT(d, DB_JOIN_ITEM); … … 7266 9617 ADD_INT(d, DB_PREV); 7267 9618 ADD_INT(d, DB_PREV_NODUP); 9619 #if (DBVER >= 46) 9620 ADD_INT(d, DB_PREV_DUP); 9621 #endif 7268 9622 #if (DBVER < 45) 7269 9623 ADD_INT(d, DB_RECORDCOUNT); … … 7281 9635 7282 9636 #if (DBVER >= 44) 9637 ADD_INT(d, DB_IMMUTABLE_KEY); 7283 9638 ADD_INT(d, DB_READ_UNCOMMITTED); /* replaces DB_DIRTY_READ in 4.4 */ 7284 9639 ADD_INT(d, DB_READ_COMMITTED); 7285 9640 #endif 7286 9641 9642 #if (DBVER >= 44) 9643 ADD_INT(d, DB_FREELIST_ONLY); 9644 ADD_INT(d, DB_FREE_SPACE); 9645 #endif 9646 7287 9647 ADD_INT(d, DB_DONOTINDEX); 7288 9648 7289 #if (DBVER >= 41)7290 _addIntToDict(d, "DB_INCOMPLETE", 0);7291 #else7292 ADD_INT(d, DB_INCOMPLETE);7293 #endif7294 9649 ADD_INT(d, DB_KEYEMPTY); 7295 9650 ADD_INT(d, DB_KEYEXIST); … … 7312 9667 ADD_INT(d, DB_NOPANIC); 7313 9668 7314 #if (DBVER >= 41)7315 9669 ADD_INT(d, DB_OVERWRITE); 7316 #endif 7317 7318 #ifdef DB_REGISTER 9670 9671 #if (DBVER >= 43) 9672 ADD_INT(d, DB_STAT_SUBSYSTEM); 9673 ADD_INT(d, DB_STAT_MEMP_HASH); 9674 #endif 9675 9676 #if (DBVER >= 48) 9677 ADD_INT(d, DB_OVERWRITE_DUP); 9678 #endif 9679 9680 #if (DBVER >= 47) 9681 ADD_INT(d, DB_FOREIGN_ABORT); 9682 ADD_INT(d, DB_FOREIGN_CASCADE); 9683 ADD_INT(d, DB_FOREIGN_NULLIFY); 9684 #endif 9685 9686 #if (DBVER >= 44) 7319 9687 ADD_INT(d, DB_REGISTER); 7320 9688 #endif 9689 9690 ADD_INT(d, DB_EID_INVALID); 9691 ADD_INT(d, DB_EID_BROADCAST); 7321 9692 7322 9693 #if (DBVER >= 42) … … 7392 9763 ADD_INT(d, DB_REP_MASTER); 7393 9764 ADD_INT(d, DB_REP_CLIENT); 9765 9766 ADD_INT(d, DB_REP_PERMANENT); 9767 9768 #if (DBVER >= 44) 9769 ADD_INT(d, DB_REP_CONF_NOAUTOINIT); 9770 ADD_INT(d, DB_REP_CONF_DELAYCLIENT); 9771 ADD_INT(d, DB_REP_CONF_BULK); 9772 ADD_INT(d, DB_REP_CONF_NOWAIT); 9773 ADD_INT(d, DB_REP_ANYWHERE); 9774 ADD_INT(d, DB_REP_REREQUEST); 9775 #endif 9776 9777 #if (DBVER >= 42) 9778 ADD_INT(d, DB_REP_NOBUFFER); 9779 #endif 9780 9781 #if (DBVER >= 46) 9782 ADD_INT(d, DB_REP_LEASE_EXPIRED); 9783 ADD_INT(d, DB_IGNORE_LEASE); 9784 #endif 9785 9786 #if (DBVER >= 47) 9787 ADD_INT(d, DB_REP_CONF_LEASE); 9788 ADD_INT(d, DB_REPMGR_CONF_2SITE_STRICT); 9789 #endif 9790 7394 9791 #if (DBVER >= 45) 7395 9792 ADD_INT(d, DB_REP_ELECTION); … … 7403 9800 ADD_INT(d, DB_REP_CHECKPOINT_DELAY); 7404 9801 ADD_INT(d, DB_REP_FULL_ELECTION_TIMEOUT); 9802 ADD_INT(d, DB_REP_LEASE_TIMEOUT); 9803 #endif 9804 #if (DBVER >= 47) 9805 ADD_INT(d, DB_REP_HEARTBEAT_MONITOR); 9806 ADD_INT(d, DB_REP_HEARTBEAT_SEND); 7405 9807 #endif 7406 9808 … … 7415 9817 ADD_INT(d, DB_REPMGR_CONNECTED); 7416 9818 ADD_INT(d, DB_REPMGR_DISCONNECTED); 7417 ADD_INT(d, DB_STAT_CLEAR);7418 9819 ADD_INT(d, DB_STAT_ALL); 7419 9820 #endif … … 7431 9832 #endif 7432 9833 7433 #if (DBVER >= 41)7434 9834 ADD_INT(d, DB_ENCRYPT_AES); 7435 9835 ADD_INT(d, DB_AUTO_COMMIT); 7436 #else 7437 /* allow Berkeley DB 4.1 aware apps to run on older versions */ 7438 _addIntToDict(d, "DB_AUTO_COMMIT", 0); 9836 ADD_INT(d, DB_PRIORITY_VERY_LOW); 9837 ADD_INT(d, DB_PRIORITY_LOW); 9838 ADD_INT(d, DB_PRIORITY_DEFAULT); 9839 ADD_INT(d, DB_PRIORITY_HIGH); 9840 ADD_INT(d, DB_PRIORITY_VERY_HIGH); 9841 9842 #if (DBVER >= 46) 9843 ADD_INT(d, DB_PRIORITY_UNCHANGED); 7439 9844 #endif 7440 9845 … … 7474 9879 PyDict_SetItemString(d, "KeyError", PyExc_KeyError); 7475 9880 PyRun_String("class DBNotFoundError(DBError, KeyError): pass\n" 7476 9881 "class DBKeyEmptyError(DBError, KeyError): pass", 7477 9882 Py_file_input, d, d); 7478 9883 DBNotFoundError = PyDict_GetItemString(d, "DBNotFoundError"); … … 7500 9905 #endif 7501 9906 7502 7503 #if !INCOMPLETE_IS_WARNING7504 MAKE_EX(DBIncompleteError);7505 #endif7506 9907 MAKE_EX(DBCursorClosedError); 7507 MAKE_EX(DBKeyEmptyError);7508 9908 MAKE_EX(DBKeyExistError); 7509 9909 MAKE_EX(DBLockDeadlockError); … … 7531 9931 MAKE_EX(DBRepHandleDeadError); 7532 9932 #endif 9933 #if (DBVER >= 44) 9934 MAKE_EX(DBRepLockoutError); 9935 #endif 7533 9936 7534 9937 MAKE_EX(DBRepUnavailError); 7535 9938 9939 #if (DBVER >= 46) 9940 MAKE_EX(DBRepLeaseExpiredError); 9941 #endif 9942 9943 #if (DBVER >= 47) 9944 MAKE_EX(DBForeignConflictError); 9945 #endif 9946 7536 9947 #undef MAKE_EX 7537 9948 7538 /* Initiliase the C API structure and add it to the module */ 7539 bsddb_api.db_type = &DB_Type; 7540 bsddb_api.dbcursor_type = &DBCursor_Type; 7541 bsddb_api.dbenv_type = &DBEnv_Type; 7542 bsddb_api.dbtxn_type = &DBTxn_Type; 7543 bsddb_api.dblock_type = &DBLock_Type; 9949 /* Initialise the C API structure and add it to the module */ 9950 bsddb_api.db_type = &DB_Type; 9951 bsddb_api.dbcursor_type = &DBCursor_Type; 9952 bsddb_api.dblogcursor_type = &DBLogCursor_Type; 9953 bsddb_api.dbenv_type = &DBEnv_Type; 9954 bsddb_api.dbtxn_type = &DBTxn_Type; 9955 bsddb_api.dblock_type = &DBLock_Type; 7544 9956 #if (DBVER >= 43) 7545 bsddb_api.dbsequence_type = &DBSequence_Type; 7546 #endif 7547 bsddb_api.makeDBError = makeDBError; 7548 9957 bsddb_api.dbsequence_type = &DBSequence_Type; 9958 #endif 9959 bsddb_api.makeDBError = makeDBError; 9960 9961 /* 9962 ** Capsules exist from Python 3.1, but I 9963 ** don't want to break the API compatibility 9964 ** for already published Python versions. 9965 */ 9966 #if (PY_VERSION_HEX < 0x03020000) 7549 9967 py_api = PyCObject_FromVoidPtr((void*)&bsddb_api, NULL); 9968 #else 9969 { 9970 char py_api_name[250]; 9971 9972 strcpy(py_api_name, _bsddbModuleName); 9973 strcat(py_api_name, ".api"); 9974 9975 py_api = PyCapsule_New((void*)&bsddb_api, py_api_name, NULL); 9976 } 9977 #endif 9978 7550 9979 PyDict_SetItemString(d, "api", py_api); 7551 9980 Py_DECREF(py_api); -
python/trunk/Modules/bsddb.h
r2 r132 71 71 * DBSequence (Sequence) 72 72 * 73 * New datatypes: 74 * 75 * DBLogCursor (Log Cursor) 76 * 73 77 */ 74 78 … … 106 110 #endif 107 111 108 #define PY_BSDDB_VERSION "4. 7.3"112 #define PY_BSDDB_VERSION "4.8.4" 109 113 110 114 /* Python object definitions */ … … 123 127 struct DBObject; /* Forward declaration */ 124 128 struct DBCursorObject; /* Forward declaration */ 129 struct DBLogCursorObject; /* Forward declaration */ 125 130 struct DBTxnObject; /* Forward declaration */ 126 131 struct DBSequenceObject; /* Forward declaration */ … … 135 140 struct DBObject *children_dbs; 136 141 struct DBTxnObject *children_txns; 142 struct DBLogCursorObject *children_logcursors; 137 143 PyObject *private_obj; 138 144 PyObject *rep_transport; … … 146 152 u_int32_t flags; /* saved flags from open() */ 147 153 u_int32_t setflags; /* saved flags from set_flags() */ 148 int haveStat;149 154 struct behaviourFlags moduleFlags; 150 155 struct DBTxnObject *txn; … … 194 199 195 200 201 typedef struct DBLogCursorObject { 202 PyObject_HEAD 203 DB_LOGC* logc; 204 DBEnvObject* env; 205 struct DBLogCursorObject **sibling_prev_p; 206 struct DBLogCursorObject *sibling_next; 207 PyObject *in_weakreflist; /* List of weak references */ 208 } DBLogCursorObject; 209 210 196 211 typedef struct { 197 212 PyObject_HEAD 198 213 DB_LOCK lock; 214 int lock_initialized; /* Signal if we actually have a lock */ 199 215 PyObject *in_weakreflist; /* List of weak references */ 200 216 } DBLockObject; … … 221 237 following (error checking missed out for clarity): 222 238 239 // If you are using Python before 3.2: 223 240 BSDDB_api* bsddb_api; 224 241 PyObject* mod; … … 232 249 Py_DECREF(mod); 233 250 251 252 // If you are using Python 3.2 or up: 253 BSDDB_api* bsddb_api; 254 255 // Use "bsddb3._pybsddb.api" if you're using 256 // the standalone pybsddb add-on. 257 bsddb_api = (void **)PyCapsule_Import("bsddb._bsddb.api", 1); 258 259 234 260 The structure's members must not be changed. 235 261 */ … … 239 265 PyTypeObject* db_type; 240 266 PyTypeObject* dbcursor_type; 267 PyTypeObject* dblogcursor_type; 241 268 PyTypeObject* dbenv_type; 242 269 PyTypeObject* dbtxn_type; … … 248 275 /* Functions */ 249 276 int (*makeDBError)(int err); 250 251 277 } BSDDB_api; 252 278 -
python/trunk/Modules/bsddbmodule.c
r2 r132 31 31 32 32 typedef struct { 33 34 35 int di_size;/* -1 means recompute */36 37 #ifdef WITH_THREAD 38 33 PyObject_HEAD 34 DB *di_bsddb; 35 int di_size; /* -1 means recompute */ 36 int di_type; 37 #ifdef WITH_THREAD 38 PyThread_type_lock di_lock; 39 39 #endif 40 40 } bsddbobject; … … 45 45 #define check_bsddbobject_open(v, r) if ((v)->di_bsddb == NULL) \ 46 46 { PyErr_SetString(BsddbError, \ 47 47 "BSDDB object has already been closed"); \ 48 48 return r; } 49 49 … … 52 52 static PyObject * 53 53 newdbhashobject(char *file, int flags, int mode, 54 55 56 { 57 58 59 60 61 62 63 64 65 66 67 68 54 int bsize, int ffactor, int nelem, int cachesize, 55 int hash, int lorder) 56 { 57 bsddbobject *dp; 58 HASHINFO info; 59 60 if ((dp = PyObject_New(bsddbobject, &Bsddbtype)) == NULL) 61 return NULL; 62 63 info.bsize = bsize; 64 info.ffactor = ffactor; 65 info.nelem = nelem; 66 info.cachesize = cachesize; 67 info.hash = NULL; /* XXX should derive from hash argument */ 68 info.lorder = lorder; 69 69 70 70 #ifdef O_BINARY 71 72 #endif 73 74 75 76 77 78 #ifdef WITH_THREAD 79 80 #endif 81 82 83 84 85 86 87 88 #ifdef WITH_THREAD 89 90 91 92 93 94 95 #endif 96 97 71 flags |= O_BINARY; 72 #endif 73 Py_BEGIN_ALLOW_THREADS 74 dp->di_bsddb = dbopen(file, flags, mode, DB_HASH, &info); 75 Py_END_ALLOW_THREADS 76 if (dp->di_bsddb == NULL) { 77 PyErr_SetFromErrno(BsddbError); 78 #ifdef WITH_THREAD 79 dp->di_lock = NULL; 80 #endif 81 Py_DECREF(dp); 82 return NULL; 83 } 84 85 dp->di_size = -1; 86 dp->di_type = DB_HASH; 87 88 #ifdef WITH_THREAD 89 dp->di_lock = PyThread_allocate_lock(); 90 if (dp->di_lock == NULL) { 91 PyErr_SetString(BsddbError, "can't allocate lock"); 92 Py_DECREF(dp); 93 return NULL; 94 } 95 #endif 96 97 return (PyObject *)dp; 98 98 } 99 99 100 100 static PyObject * 101 101 newdbbtobject(char *file, int flags, int mode, 102 103 104 { 105 106 107 108 109 110 111 112 113 114 115 116 117 118 102 int btflags, int cachesize, int maxkeypage, 103 int minkeypage, int psize, int lorder) 104 { 105 bsddbobject *dp; 106 BTREEINFO info; 107 108 if ((dp = PyObject_New(bsddbobject, &Bsddbtype)) == NULL) 109 return NULL; 110 111 info.flags = btflags; 112 info.cachesize = cachesize; 113 info.maxkeypage = maxkeypage; 114 info.minkeypage = minkeypage; 115 info.psize = psize; 116 info.lorder = lorder; 117 info.compare = 0; /* Use default comparison functions, for now..*/ 118 info.prefix = 0; 119 119 120 120 #ifdef O_BINARY 121 122 #endif 123 124 125 126 127 128 #ifdef WITH_THREAD 129 130 #endif 131 132 133 134 135 136 137 138 #ifdef WITH_THREAD 139 140 141 142 143 144 145 #endif 146 147 121 flags |= O_BINARY; 122 #endif 123 Py_BEGIN_ALLOW_THREADS 124 dp->di_bsddb = dbopen(file, flags, mode, DB_BTREE, &info); 125 Py_END_ALLOW_THREADS 126 if (dp->di_bsddb == NULL) { 127 PyErr_SetFromErrno(BsddbError); 128 #ifdef WITH_THREAD 129 dp->di_lock = NULL; 130 #endif 131 Py_DECREF(dp); 132 return NULL; 133 } 134 135 dp->di_size = -1; 136 dp->di_type = DB_BTREE; 137 138 #ifdef WITH_THREAD 139 dp->di_lock = PyThread_allocate_lock(); 140 if (dp->di_lock == NULL) { 141 PyErr_SetString(BsddbError, "can't allocate lock"); 142 Py_DECREF(dp); 143 return NULL; 144 } 145 #endif 146 147 return (PyObject *)dp; 148 148 } 149 149 150 150 static PyObject * 151 151 newdbrnobject(char *file, int flags, int mode, 152 153 154 { 155 156 157 158 159 160 161 162 163 164 165 166 167 168 152 int rnflags, int cachesize, int psize, int lorder, 153 size_t reclen, u_char bval, char *bfname) 154 { 155 bsddbobject *dp; 156 RECNOINFO info; 157 int fd; 158 159 if ((dp = PyObject_New(bsddbobject, &Bsddbtype)) == NULL) 160 return NULL; 161 162 info.flags = rnflags; 163 info.cachesize = cachesize; 164 info.psize = psize; 165 info.lorder = lorder; 166 info.reclen = reclen; 167 info.bval = bval; 168 info.bfname = bfname; 169 169 170 170 #ifdef O_BINARY 171 172 #endif 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 #ifdef WITH_THREAD 188 189 #endif 190 191 192 193 194 195 196 197 #ifdef WITH_THREAD 198 199 200 201 202 203 204 #endif 205 206 171 flags |= O_BINARY; 172 #endif 173 /* This is a hack to avoid a dbopen() bug that happens when 174 * it fails. */ 175 fd = open(file, flags); 176 if (fd == -1) { 177 dp->di_bsddb = NULL; 178 } 179 else { 180 close(fd); 181 Py_BEGIN_ALLOW_THREADS 182 dp->di_bsddb = dbopen(file, flags, mode, DB_RECNO, &info); 183 Py_END_ALLOW_THREADS 184 } 185 if (dp->di_bsddb == NULL) { 186 PyErr_SetFromErrno(BsddbError); 187 #ifdef WITH_THREAD 188 dp->di_lock = NULL; 189 #endif 190 Py_DECREF(dp); 191 return NULL; 192 } 193 194 dp->di_size = -1; 195 dp->di_type = DB_RECNO; 196 197 #ifdef WITH_THREAD 198 dp->di_lock = PyThread_allocate_lock(); 199 if (dp->di_lock == NULL) { 200 PyErr_SetString(BsddbError, "can't allocate lock"); 201 Py_DECREF(dp); 202 return NULL; 203 } 204 #endif 205 206 return (PyObject *)dp; 207 207 } 208 208 … … 211 211 { 212 212 #ifdef WITH_THREAD 213 214 215 216 217 218 219 #endif 220 221 222 223 224 225 226 227 228 229 230 213 if (dp->di_lock) { 214 PyThread_acquire_lock(dp->di_lock, 0); 215 PyThread_release_lock(dp->di_lock); 216 PyThread_free_lock(dp->di_lock); 217 dp->di_lock = NULL; 218 } 219 #endif 220 if (dp->di_bsddb != NULL) { 221 int status; 222 Py_BEGIN_ALLOW_THREADS 223 status = (dp->di_bsddb->close)(dp->di_bsddb); 224 Py_END_ALLOW_THREADS 225 if (status != 0) 226 fprintf(stderr, 227 "Python bsddb: close errno %d in dealloc\n", 228 errno); 229 } 230 PyObject_Del(dp); 231 231 } 232 232 233 233 #ifdef WITH_THREAD 234 234 #define BSDDB_BGN_SAVE(_dp) \ 235 235 Py_BEGIN_ALLOW_THREADS PyThread_acquire_lock(_dp->di_lock,1); 236 236 #define BSDDB_END_SAVE(_dp) \ 237 237 PyThread_release_lock(_dp->di_lock); Py_END_ALLOW_THREADS 238 238 #else 239 #define BSDDB_BGN_SAVE(_dp) Py_BEGIN_ALLOW_THREADS 239 #define BSDDB_BGN_SAVE(_dp) Py_BEGIN_ALLOW_THREADS 240 240 #define BSDDB_END_SAVE(_dp) Py_END_ALLOW_THREADS 241 241 #endif … … 244 244 bsddb_length(bsddbobject *dp) 245 245 { 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 246 check_bsddbobject_open(dp, -1); 247 if (dp->di_size < 0) { 248 DBT krec, drec; 249 int status; 250 int size = 0; 251 BSDDB_BGN_SAVE(dp) 252 for (status = (dp->di_bsddb->seq)(dp->di_bsddb, 253 &krec, &drec,R_FIRST); 254 status == 0; 255 status = (dp->di_bsddb->seq)(dp->di_bsddb, 256 &krec, &drec, R_NEXT)) 257 size++; 258 BSDDB_END_SAVE(dp) 259 if (status < 0) { 260 PyErr_SetFromErrno(BsddbError); 261 return -1; 262 } 263 dp->di_size = size; 264 } 265 return dp->di_size; 266 266 } 267 267 … … 269 269 bsddb_subscript(bsddbobject *dp, PyObject *key) 270 270 { 271 int status; 272 DBT krec, drec; 273 char *data,buf[4096]; 274 int size; 275 PyObject *result; 276 recno_t recno; 277 278 if (dp->di_type == DB_RECNO) { 279 if (!PyArg_Parse(key, "i", &recno)) { 280 PyErr_SetString(PyExc_TypeError, 281 "key type must be integer"); 282 return NULL; 283 } 284 krec.data = &recno; 285 krec.size = sizeof(recno); 286 } 287 else { 288 if (!PyArg_Parse(key, "s#", &data, &size)) { 289 PyErr_SetString(PyExc_TypeError, 290 "key type must be string"); 291 return NULL; 292 } 293 krec.data = data; 294 krec.size = size; 295 } 296 check_bsddbobject_open(dp, NULL); 297 298 BSDDB_BGN_SAVE(dp) 299 status = (dp->di_bsddb->get)(dp->di_bsddb, &krec, &drec, 0); 300 if (status == 0) { 301 if (drec.size > sizeof(buf)) data = malloc(drec.size); 302 else data = buf; 303 if (data!=NULL) memcpy(data,drec.data,drec.size); 304 } 305 BSDDB_END_SAVE(dp) 306 if (data==NULL) return PyErr_NoMemory(); 307 if (status != 0) { 308 if (status < 0) 309 PyErr_SetFromErrno(BsddbError); 310 else 311 PyErr_SetObject(PyExc_KeyError, key); 312 return NULL; 313 } 314 315 result = PyString_FromStringAndSize(data, (int)drec.size); 316 if (data != buf) free(data); 317 return result; 271 int status; 272 DBT krec, drec; 273 char *data = NULL; 274 char buf[4096]; 275 int size; 276 PyObject *result; 277 recno_t recno; 278 279 if (dp->di_type == DB_RECNO) { 280 if (!PyArg_Parse(key, "i", &recno)) { 281 PyErr_SetString(PyExc_TypeError, 282 "key type must be integer"); 283 return NULL; 284 } 285 krec.data = &recno; 286 krec.size = sizeof(recno); 287 } 288 else { 289 if (!PyArg_Parse(key, "s#", &data, &size)) { 290 PyErr_SetString(PyExc_TypeError, 291 "key type must be string"); 292 return NULL; 293 } 294 krec.data = data; 295 krec.size = size; 296 } 297 check_bsddbobject_open(dp, NULL); 298 299 BSDDB_BGN_SAVE(dp) 300 status = (dp->di_bsddb->get)(dp->di_bsddb, &krec, &drec, 0); 301 if (status == 0) { 302 if (drec.size > sizeof(buf)) data = malloc(drec.size); 303 else data = buf; 304 if (data!=NULL) memcpy(data,drec.data,drec.size); 305 } 306 BSDDB_END_SAVE(dp) 307 if (data==NULL) return PyErr_NoMemory(); 308 if (status != 0) { 309 if (status < 0) 310 PyErr_SetFromErrno(BsddbError); 311 else 312 PyErr_SetObject(PyExc_KeyError, key); 313 return NULL; 314 } 315 316 result = PyString_FromStringAndSize(data, (int)drec.size); 317 if (data != buf) free(data); 318 return result; 318 319 } 319 320 … … 321 322 bsddb_ass_sub(bsddbobject *dp, PyObject *key, PyObject *value) 322 323 { 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 324 int status; 325 DBT krec, drec; 326 char *data; 327 int size; 328 recno_t recno; 329 330 if (dp->di_type == DB_RECNO) { 331 if (!PyArg_Parse(key, "i", &recno)) { 332 PyErr_SetString(PyExc_TypeError, 333 "bsddb key type must be integer"); 334 return -1; 335 } 336 krec.data = &recno; 337 krec.size = sizeof(recno); 338 } 339 else { 340 if (!PyArg_Parse(key, "s#", &data, &size)) { 341 PyErr_SetString(PyExc_TypeError, 342 "bsddb key type must be string"); 343 return -1; 344 } 345 krec.data = data; 346 krec.size = size; 347 } 348 check_bsddbobject_open(dp, -1); 349 dp->di_size = -1; 350 if (value == NULL) { 351 BSDDB_BGN_SAVE(dp) 352 status = (dp->di_bsddb->del)(dp->di_bsddb, &krec, 0); 353 BSDDB_END_SAVE(dp) 354 } 355 else { 356 if (!PyArg_Parse(value, "s#", &data, &size)) { 357 PyErr_SetString(PyExc_TypeError, 358 "bsddb value type must be string"); 359 return -1; 360 } 361 drec.data = data; 362 drec.size = size; 363 BSDDB_BGN_SAVE(dp) 364 status = (dp->di_bsddb->put)(dp->di_bsddb, &krec, &drec, 0); 365 BSDDB_END_SAVE(dp) 366 } 367 if (status != 0) { 368 if (status < 0) 369 PyErr_SetFromErrno(BsddbError); 370 else 371 PyErr_SetObject(PyExc_KeyError, key); 372 return -1; 373 } 374 return 0; 374 375 } 375 376 376 377 static PyMappingMethods bsddb_as_mapping = { 377 (lenfunc)bsddb_length,/*mp_length*/378 (binaryfunc)bsddb_subscript,/*mp_subscript*/379 (objobjargproc)bsddb_ass_sub,/*mp_ass_subscript*/378 (lenfunc)bsddb_length, /*mp_length*/ 379 (binaryfunc)bsddb_subscript, /*mp_subscript*/ 380 (objobjargproc)bsddb_ass_sub, /*mp_ass_subscript*/ 380 381 }; 381 382 … … 383 384 bsddb_close(bsddbobject *dp) 384 385 { 385 386 387 388 389 390 391 392 393 394 395 396 397 398 386 if (dp->di_bsddb != NULL) { 387 int status; 388 BSDDB_BGN_SAVE(dp) 389 status = (dp->di_bsddb->close)(dp->di_bsddb); 390 BSDDB_END_SAVE(dp) 391 if (status != 0) { 392 dp->di_bsddb = NULL; 393 PyErr_SetFromErrno(BsddbError); 394 return NULL; 395 } 396 } 397 dp->di_bsddb = NULL; 398 Py_INCREF(Py_None); 399 return Py_None; 399 400 } 400 401 … … 402 403 bsddb_keys(bsddbobject *dp) 403 404 { 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431 432 433 434 435 436 437 438 439 440 441 442 443 444 445 446 447 448 449 450 451 452 453 454 455 456 457 458 459 460 405 PyObject *list, *item=NULL; 406 DBT krec, drec; 407 char *data=NULL,buf[4096]; 408 int status; 409 int err; 410 411 check_bsddbobject_open(dp, NULL); 412 list = PyList_New(0); 413 if (list == NULL) 414 return NULL; 415 BSDDB_BGN_SAVE(dp) 416 status = (dp->di_bsddb->seq)(dp->di_bsddb, &krec, &drec, R_FIRST); 417 if (status == 0) { 418 if (krec.size > sizeof(buf)) data = malloc(krec.size); 419 else data = buf; 420 if (data != NULL) memcpy(data,krec.data,krec.size); 421 } 422 BSDDB_END_SAVE(dp) 423 if (status == 0 && data==NULL) return PyErr_NoMemory(); 424 while (status == 0) { 425 if (dp->di_type == DB_RECNO) 426 item = PyInt_FromLong(*((int*)data)); 427 else 428 item = PyString_FromStringAndSize(data, 429 (int)krec.size); 430 if (data != buf) free(data); 431 if (item == NULL) { 432 Py_DECREF(list); 433 return NULL; 434 } 435 err = PyList_Append(list, item); 436 Py_DECREF(item); 437 if (err != 0) { 438 Py_DECREF(list); 439 return NULL; 440 } 441 BSDDB_BGN_SAVE(dp) 442 status = (dp->di_bsddb->seq) 443 (dp->di_bsddb, &krec, &drec, R_NEXT); 444 if (status == 0) { 445 if (krec.size > sizeof(buf)) 446 data = malloc(krec.size); 447 else data = buf; 448 if (data != NULL) 449 memcpy(data,krec.data,krec.size); 450 } 451 BSDDB_END_SAVE(dp) 452 if (data == NULL) return PyErr_NoMemory(); 453 } 454 if (status < 0) { 455 PyErr_SetFromErrno(BsddbError); 456 Py_DECREF(list); 457 return NULL; 458 } 459 if (dp->di_size < 0) 460 dp->di_size = PyList_Size(list); /* We just did the work */ 461 return list; 461 462 } 462 463 … … 464 465 bsddb_has_key(bsddbobject *dp, PyObject *args) 465 466 { 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 467 DBT krec, drec; 468 int status; 469 char *data; 470 int size; 471 recno_t recno; 472 473 if (dp->di_type == DB_RECNO) { 474 if (!PyArg_ParseTuple(args, "i;key type must be integer", 475 &recno)) { 476 return NULL; 477 } 478 krec.data = &recno; 479 krec.size = sizeof(recno); 480 } 481 else { 482 if (!PyArg_ParseTuple(args, "s#;key type must be string", 483 &data, &size)) { 484 return NULL; 485 } 486 krec.data = data; 487 krec.size = size; 488 } 489 check_bsddbobject_open(dp, NULL); 490 491 BSDDB_BGN_SAVE(dp) 492 status = (dp->di_bsddb->get)(dp->di_bsddb, &krec, &drec, 0); 493 BSDDB_END_SAVE(dp) 494 if (status < 0) { 495 PyErr_SetFromErrno(BsddbError); 496 return NULL; 497 } 498 499 return PyInt_FromLong(status == 0); 499 500 } 500 501 … … 502 503 bsddb_set_location(bsddbobject *dp, PyObject *key) 503 504 { 504 int status; 505 DBT krec, drec; 506 char *data,buf[4096]; 507 int size; 508 PyObject *result; 509 recno_t recno; 510 511 if (dp->di_type == DB_RECNO) { 512 if (!PyArg_ParseTuple(key, "i;key type must be integer", 513 &recno)) { 514 return NULL; 515 } 516 krec.data = &recno; 517 krec.size = sizeof(recno); 518 } 519 else { 520 if (!PyArg_ParseTuple(key, "s#;key type must be string", 521 &data, &size)) { 522 return NULL; 523 } 524 krec.data = data; 525 krec.size = size; 526 } 527 check_bsddbobject_open(dp, NULL); 528 529 BSDDB_BGN_SAVE(dp) 530 status = (dp->di_bsddb->seq)(dp->di_bsddb, &krec, &drec, R_CURSOR); 531 if (status == 0) { 532 if (drec.size > sizeof(buf)) data = malloc(drec.size); 533 else data = buf; 534 if (data!=NULL) memcpy(data,drec.data,drec.size); 535 } 536 BSDDB_END_SAVE(dp) 537 if (data==NULL) return PyErr_NoMemory(); 538 if (status != 0) { 539 if (status < 0) 540 PyErr_SetFromErrno(BsddbError); 541 else 542 PyErr_SetObject(PyExc_KeyError, key); 543 return NULL; 544 } 545 546 if (dp->di_type == DB_RECNO) 547 result = Py_BuildValue("is#", *((int*)krec.data), 548 data, drec.size); 549 else 550 result = Py_BuildValue("s#s#", krec.data, krec.size, 551 data, drec.size); 552 if (data != buf) free(data); 553 return result; 505 int status; 506 DBT krec, drec; 507 char *data = NULL; 508 char buf[4096]; 509 int size; 510 PyObject *result; 511 recno_t recno; 512 513 if (dp->di_type == DB_RECNO) { 514 if (!PyArg_ParseTuple(key, "i;key type must be integer", 515 &recno)) { 516 return NULL; 517 } 518 krec.data = &recno; 519 krec.size = sizeof(recno); 520 } 521 else { 522 if (!PyArg_ParseTuple(key, "s#;key type must be string", 523 &data, &size)) { 524 return NULL; 525 } 526 krec.data = data; 527 krec.size = size; 528 } 529 check_bsddbobject_open(dp, NULL); 530 531 BSDDB_BGN_SAVE(dp) 532 status = (dp->di_bsddb->seq)(dp->di_bsddb, &krec, &drec, R_CURSOR); 533 if (status == 0) { 534 if (drec.size > sizeof(buf)) data = malloc(drec.size); 535 else data = buf; 536 if (data!=NULL) memcpy(data,drec.data,drec.size); 537 } 538 BSDDB_END_SAVE(dp) 539 if (data==NULL) return PyErr_NoMemory(); 540 if (status != 0) { 541 if (status < 0) 542 PyErr_SetFromErrno(BsddbError); 543 else 544 PyErr_SetObject(PyExc_KeyError, key); 545 return NULL; 546 } 547 548 if (dp->di_type == DB_RECNO) 549 result = Py_BuildValue("is#", *((int*)krec.data), 550 data, drec.size); 551 else 552 result = Py_BuildValue("s#s#", krec.data, krec.size, 553 data, drec.size); 554 if (data != buf) free(data); 555 return result; 554 556 } 555 557 … … 557 559 bsddb_seq(bsddbobject *dp, int sequence_request) 558 560 { 559 560 561 562 563 564 565 566 567 568 569 570 571 572 573 574 575 576 577 578 579 580 581 582 if ((kdata == NULL) || (ddata == NULL)) 583 584 585 else { 586 /* (status != 0) */ 587 588 589 590 591 592 593 594 595 596 597 598 599 600 601 602 561 int status; 562 DBT krec, drec; 563 char *kdata=NULL,kbuf[4096]; 564 char *ddata=NULL,dbuf[4096]; 565 PyObject *result; 566 567 check_bsddbobject_open(dp, NULL); 568 krec.data = 0; 569 krec.size = 0; 570 571 BSDDB_BGN_SAVE(dp) 572 status = (dp->di_bsddb->seq)(dp->di_bsddb, &krec, 573 &drec, sequence_request); 574 if (status == 0) { 575 if (krec.size > sizeof(kbuf)) kdata = malloc(krec.size); 576 else kdata = kbuf; 577 if (kdata != NULL) memcpy(kdata,krec.data,krec.size); 578 if (drec.size > sizeof(dbuf)) ddata = malloc(drec.size); 579 else ddata = dbuf; 580 if (ddata != NULL) memcpy(ddata,drec.data,drec.size); 581 } 582 BSDDB_END_SAVE(dp) 583 if (status == 0) { 584 if ((kdata == NULL) || (ddata == NULL)) 585 return PyErr_NoMemory(); 586 } 587 else { 588 /* (status != 0) */ 589 if (status < 0) 590 PyErr_SetFromErrno(BsddbError); 591 else 592 PyErr_SetString(PyExc_KeyError, "no key/data pairs"); 593 return NULL; 594 } 595 596 if (dp->di_type == DB_RECNO) 597 result = Py_BuildValue("is#", *((int*)kdata), 598 ddata, drec.size); 599 else 600 result = Py_BuildValue("s#s#", kdata, krec.size, 601 ddata, drec.size); 602 if (kdata != kbuf) free(kdata); 603 if (ddata != dbuf) free(ddata); 604 return result; 603 605 } 604 606 … … 606 608 bsddb_next(bsddbobject *dp) 607 609 { 608 610 return bsddb_seq(dp, R_NEXT); 609 611 } 610 612 static PyObject * 611 613 bsddb_previous(bsddbobject *dp) 612 614 { 613 615 return bsddb_seq(dp, R_PREV); 614 616 } 615 617 static PyObject * 616 618 bsddb_first(bsddbobject *dp) 617 619 { 618 620 return bsddb_seq(dp, R_FIRST); 619 621 } 620 622 static PyObject * 621 623 bsddb_last(bsddbobject *dp) 622 624 { 623 625 return bsddb_seq(dp, R_LAST); 624 626 } 625 627 static PyObject * 626 628 bsddb_sync(bsddbobject *dp) 627 629 { 628 629 630 631 632 633 634 635 636 637 638 return PyInt_FromLong(status =0);630 int status; 631 632 check_bsddbobject_open(dp, NULL); 633 BSDDB_BGN_SAVE(dp) 634 status = (dp->di_bsddb->sync)(dp->di_bsddb, 0); 635 BSDDB_END_SAVE(dp) 636 if (status != 0) { 637 PyErr_SetFromErrno(BsddbError); 638 return NULL; 639 } 640 return PyInt_FromLong(0); 639 641 } 640 642 static PyMethodDef bsddb_methods[] = { 641 {"close",(PyCFunction)bsddb_close, METH_NOARGS},642 {"keys",(PyCFunction)bsddb_keys, METH_NOARGS},643 {"has_key",(PyCFunction)bsddb_has_key, METH_VARARGS},644 {"set_location",(PyCFunction)bsddb_set_location, METH_VARARGS},645 {"next",(PyCFunction)bsddb_next, METH_NOARGS},646 {"previous",(PyCFunction)bsddb_previous, METH_NOARGS},647 {"first",(PyCFunction)bsddb_first, METH_NOARGS},648 {"last",(PyCFunction)bsddb_last, METH_NOARGS},649 {"sync",(PyCFunction)bsddb_sync, METH_NOARGS},650 {NULL, NULL}/* sentinel */643 {"close", (PyCFunction)bsddb_close, METH_NOARGS}, 644 {"keys", (PyCFunction)bsddb_keys, METH_NOARGS}, 645 {"has_key", (PyCFunction)bsddb_has_key, METH_VARARGS}, 646 {"set_location", (PyCFunction)bsddb_set_location, METH_VARARGS}, 647 {"next", (PyCFunction)bsddb_next, METH_NOARGS}, 648 {"previous", (PyCFunction)bsddb_previous, METH_NOARGS}, 649 {"first", (PyCFunction)bsddb_first, METH_NOARGS}, 650 {"last", (PyCFunction)bsddb_last, METH_NOARGS}, 651 {"sync", (PyCFunction)bsddb_sync, METH_NOARGS}, 652 {NULL, NULL} /* sentinel */ 651 653 }; 652 654 … … 654 656 bsddb_getattr(PyObject *dp, char *name) 655 657 { 656 658 return Py_FindMethod(bsddb_methods, dp, name); 657 659 } 658 660 659 661 static PyTypeObject Bsddbtype = { 660 661 662 663 664 665 666 0,/*tp_print*/667 668 0,/*tp_setattr*/669 0,/*tp_compare*/670 0,/*tp_repr*/671 0,/*tp_as_number*/672 0,/*tp_as_sequence*/673 &bsddb_as_mapping,/*tp_as_mapping*/662 PyObject_HEAD_INIT(NULL) 663 0, 664 "bsddb.bsddb", 665 sizeof(bsddbobject), 666 0, 667 (destructor)bsddb_dealloc, /*tp_dealloc*/ 668 0, /*tp_print*/ 669 (getattrfunc)bsddb_getattr, /*tp_getattr*/ 670 0, /*tp_setattr*/ 671 0, /*tp_compare*/ 672 0, /*tp_repr*/ 673 0, /*tp_as_number*/ 674 0, /*tp_as_sequence*/ 675 &bsddb_as_mapping, /*tp_as_mapping*/ 674 676 }; 675 677 … … 677 679 bsdhashopen(PyObject *self, PyObject *args) 678 680 { 679 680 681 682 683 684 685 686 687 688 689 690 691 692 693 694 695 696 697 698 699 700 701 702 703 704 705 706 707 708 709 710 681 char *file; 682 char *flag = NULL; 683 int flags = O_RDONLY; 684 int mode = 0666; 685 int bsize = 0; 686 int ffactor = 0; 687 int nelem = 0; 688 int cachesize = 0; 689 int hash = 0; /* XXX currently ignored */ 690 int lorder = 0; 691 692 if (!PyArg_ParseTuple(args, "z|siiiiiii:hashopen", 693 &file, &flag, &mode, 694 &bsize, &ffactor, &nelem, &cachesize, 695 &hash, &lorder)) 696 return NULL; 697 if (flag != NULL) { 698 /* XXX need to pass O_EXCL, O_EXLOCK, O_NONBLOCK, O_SHLOCK */ 699 if (flag[0] == 'r') 700 flags = O_RDONLY; 701 else if (flag[0] == 'w') 702 flags = O_RDWR; 703 else if (flag[0] == 'c') 704 flags = O_RDWR|O_CREAT; 705 else if (flag[0] == 'n') 706 flags = O_RDWR|O_CREAT|O_TRUNC; 707 else { 708 PyErr_SetString(BsddbError, 709 "Flag should begin with 'r', 'w', 'c' or 'n'"); 710 return NULL; 711 } 712 if (flag[1] == 'l') { 711 713 #if defined(O_EXLOCK) && defined(O_SHLOCK) 712 713 714 715 714 if (flag[0] == 'r') 715 flags |= O_SHLOCK; 716 else 717 flags |= O_EXLOCK; 716 718 #else 717 718 719 720 #endif 721 722 723 724 719 PyErr_SetString(BsddbError, 720 "locking not supported on this platform"); 721 return NULL; 722 #endif 723 } 724 } 725 return newdbhashobject(file, flags, mode, 726 bsize, ffactor, nelem, cachesize, hash, lorder); 725 727 } 726 728 … … 728 730 bsdbtopen(PyObject *self, PyObject *args) 729 731 { 730 731 732 733 734 735 736 737 738 739 740 741 742 743 744 745 746 747 748 749 750 751 752 753 754 755 756 757 758 759 760 761 732 char *file; 733 char *flag = NULL; 734 int flags = O_RDONLY; 735 int mode = 0666; 736 int cachesize = 0; 737 int maxkeypage = 0; 738 int minkeypage = 0; 739 int btflags = 0; 740 unsigned int psize = 0; 741 int lorder = 0; 742 743 if (!PyArg_ParseTuple(args, "z|siiiiiii:btopen", 744 &file, &flag, &mode, 745 &btflags, &cachesize, &maxkeypage, &minkeypage, 746 &psize, &lorder)) 747 return NULL; 748 if (flag != NULL) { 749 /* XXX need to pass O_EXCL, O_EXLOCK, O_NONBLOCK, O_SHLOCK */ 750 if (flag[0] == 'r') 751 flags = O_RDONLY; 752 else if (flag[0] == 'w') 753 flags = O_RDWR; 754 else if (flag[0] == 'c') 755 flags = O_RDWR|O_CREAT; 756 else if (flag[0] == 'n') 757 flags = O_RDWR|O_CREAT|O_TRUNC; 758 else { 759 PyErr_SetString(BsddbError, 760 "Flag should begin with 'r', 'w', 'c' or 'n'"); 761 return NULL; 762 } 763 if (flag[1] == 'l') { 762 764 #if defined(O_EXLOCK) && defined(O_SHLOCK) 763 764 765 766 765 if (flag[0] == 'r') 766 flags |= O_SHLOCK; 767 else 768 flags |= O_EXLOCK; 767 769 #else 768 769 770 771 #endif 772 773 774 775 776 770 PyErr_SetString(BsddbError, 771 "locking not supported on this platform"); 772 return NULL; 773 #endif 774 } 775 } 776 return newdbbtobject(file, flags, mode, 777 btflags, cachesize, maxkeypage, minkeypage, 778 psize, lorder); 777 779 } 778 780 … … 780 782 bsdrnopen(PyObject *self, PyObject *args) 781 783 { 782 783 784 785 786 787 788 789 790 791 792 793 794 795 796 797 798 799 800 801 802 803 804 805 806 807 808 809 810 811 812 813 814 815 784 char *file; 785 char *flag = NULL; 786 int flags = O_RDONLY; 787 int mode = 0666; 788 int cachesize = 0; 789 int rnflags = 0; 790 unsigned int psize = 0; 791 int lorder = 0; 792 size_t reclen = 0; 793 char *bval = ""; 794 char *bfname = NULL; 795 796 if (!PyArg_ParseTuple(args, "z|siiiiiiss:rnopen", 797 &file, &flag, &mode, 798 &rnflags, &cachesize, &psize, &lorder, 799 &reclen, &bval, &bfname)) 800 return NULL; 801 802 if (flag != NULL) { 803 /* XXX need to pass O_EXCL, O_EXLOCK, O_NONBLOCK, O_SHLOCK */ 804 if (flag[0] == 'r') 805 flags = O_RDONLY; 806 else if (flag[0] == 'w') 807 flags = O_RDWR; 808 else if (flag[0] == 'c') 809 flags = O_RDWR|O_CREAT; 810 else if (flag[0] == 'n') 811 flags = O_RDWR|O_CREAT|O_TRUNC; 812 else { 813 PyErr_SetString(BsddbError, 814 "Flag should begin with 'r', 'w', 'c' or 'n'"); 815 return NULL; 816 } 817 if (flag[1] == 'l') { 816 818 #if defined(O_EXLOCK) && defined(O_SHLOCK) 817 818 819 820 819 if (flag[0] == 'r') 820 flags |= O_SHLOCK; 821 else 822 flags |= O_EXLOCK; 821 823 #else 822 823 824 825 #endif 826 827 828 829 830 831 832 833 834 824 PyErr_SetString(BsddbError, 825 "locking not supported on this platform"); 826 return NULL; 827 #endif 828 } 829 else if (flag[1] != '\0') { 830 PyErr_SetString(BsddbError, 831 "Flag char 2 should be 'l' or absent"); 832 return NULL; 833 } 834 } 835 return newdbrnobject(file, flags, mode, rnflags, cachesize, 836 psize, lorder, reclen, bval[0], bfname); 835 837 } 836 838 837 839 static PyMethodDef bsddbmodule_methods[] = { 838 {"hashopen",(PyCFunction)bsdhashopen, METH_VARARGS},839 {"btopen",(PyCFunction)bsdbtopen, METH_VARARGS},840 {"rnopen",(PyCFunction)bsdrnopen, METH_VARARGS},841 842 {"open",(PyCFunction)bsdhashopen, METH_VARARGS},843 {0,0},840 {"hashopen", (PyCFunction)bsdhashopen, METH_VARARGS}, 841 {"btopen", (PyCFunction)bsdbtopen, METH_VARARGS}, 842 {"rnopen", (PyCFunction)bsdrnopen, METH_VARARGS}, 843 /* strictly for use by dbhhash!!! */ 844 {"open", (PyCFunction)bsdhashopen, METH_VARARGS}, 845 {0, 0}, 844 846 }; 845 847 846 848 PyMODINIT_FUNC 847 849 initbsddb185(void) { 848 850 PyObject *m, *d; 849 851 850 852 if (PyErr_WarnPy3k("the bsddb185 module has been removed in " 851 853 "Python 3.0", 2) < 0) 852 return;853 854 855 856 857 858 859 860 861 862 } 854 return; 855 856 Bsddbtype.ob_type = &PyType_Type; 857 m = Py_InitModule("bsddb185", bsddbmodule_methods); 858 if (m == NULL) 859 return; 860 d = PyModule_GetDict(m); 861 BsddbError = PyErr_NewException("bsddb.error", NULL, NULL); 862 if (BsddbError != NULL) 863 PyDict_SetItemString(d, "error", BsddbError); 864 } -
python/trunk/setup.py
r27 r132 713 713 # versions of BerkeleyDB already installed. 714 714 715 max_db_ver = (4, 7)715 max_db_ver = (4, 8) 716 716 min_db_ver = (3, 3) 717 db_setup_debug = False # verbose debug prints from this script?717 db_setup_debug = True # verbose debug prints from this script? 718 718 719 719 def allow_db_ver(db_ver):
Note:
See TracChangeset
for help on using the changeset viewer.