diff options
author | Lorry Tar Creator <lorry-tar-importer@baserock.org> | 2015-02-17 17:25:57 +0000 |
---|---|---|
committer | <> | 2015-03-17 16:26:24 +0000 |
commit | 780b92ada9afcf1d58085a83a0b9e6bc982203d1 (patch) | |
tree | 598f8b9fa431b228d29897e798de4ac0c1d3d970 /lang/tcl/tcl_db_pkg.c | |
parent | 7a2660ba9cc2dc03a69ddfcfd95369395cc87444 (diff) | |
download | berkeleydb-master.tar.gz |
Diffstat (limited to 'lang/tcl/tcl_db_pkg.c')
-rw-r--r-- | lang/tcl/tcl_db_pkg.c | 560 |
1 files changed, 499 insertions, 61 deletions
diff --git a/lang/tcl/tcl_db_pkg.c b/lang/tcl/tcl_db_pkg.c index a190f9de..6de1e449 100644 --- a/lang/tcl/tcl_db_pkg.c +++ b/lang/tcl/tcl_db_pkg.c @@ -1,7 +1,7 @@ /*- * See the file LICENSE for redistribution information. * - * Copyright (c) 1999, 2012 Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 1999, 2015 Oracle and/or its affiliates. All rights reserved. * * $Id$ */ @@ -47,16 +47,17 @@ static int bdb_GetConfig __P((Tcl_Interp *, int, Tcl_Obj * CONST*)); static int bdb_Handles __P((Tcl_Interp *, int, Tcl_Obj * CONST*)); static int bdb_MsgType __P((Tcl_Interp *, int, Tcl_Obj * CONST*)); -static int tcl_bt_compare __P((DB *, const DBT *, const DBT *)); +static int tcl_bt_compare __P((DB *, const DBT *, const DBT *, size_t *)); static int tcl_compare_callback __P((DB *, const DBT *, const DBT *, Tcl_Obj *, char *)); static void tcl_db_free __P((void *)); static void * tcl_db_malloc __P((size_t)); static void * tcl_db_realloc __P((void *, size_t)); -static int tcl_dup_compare __P((DB *, const DBT *, const DBT *)); +static int tcl_dup_compare __P((DB *, const DBT *, const DBT *, size_t *)); static u_int32_t tcl_h_hash __P((DB *, const void *, u_int32_t)); static int tcl_isalive __P((DB_ENV *, pid_t, db_threadid_t, u_int32_t)); static u_int32_t tcl_part_callback __P((DB *, DBT *)); +static int tcl_rep_view __P((DB_ENV *, const char *, int *, u_int32_t)); static int tcl_set_partition_dirs __P((Tcl_Interp *, DB *, Tcl_Obj *)); static int tcl_set_partition_keys @@ -219,6 +220,7 @@ berkdb_Cmd(notused, interp, objc, objv) COMPQUIET(hrip, NULL); COMPQUIET(hsdbp, NULL); COMPQUIET(hsip, NULL); + COMPQUIET(dbenv, NULL); Tcl_ResetResult(interp); memset(newname, 0, MSG_SIZE); @@ -476,9 +478,11 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) "-lock", "-lock_conflict", "-lock_detect", - "-lock_locks", "-lock_lockers", + "-lock_locks", + "-lock_logid", "-lock_objects", + "-lock_thread", "-lock_max_locks", "-lock_max_lockers", "-lock_max_objects", @@ -487,6 +491,7 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) "-lock_timeout", "-log", "-log_filemode", + "-log_blob", "-log_buffer", "-log_inmemory", "-log_max", @@ -499,6 +504,7 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) "-mpool_mutex_count", "-mpool_nommap", "-multiversion", + "-mutex_failchk_timeout", "-mutex_set_align", "-mutex_set_incr", "-mutex_set_init", @@ -511,11 +517,18 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) "-region_init", "-rep", "-rep_client", + "-rep_config", "-rep_inmem_files", "-rep_lease", + "-rep_limit", "-rep_master", "-rep_nsites", + "-rep_priority", + "-rep_request", + "-rep_timeout", "-rep_transport", + "-rep_view", + "-repmgr_ack_policy", "-set_intermediate_dir_mode", "-snapshot", "-tablesize", @@ -530,6 +543,8 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) "-zero_log", #endif "-add_dir", + "-blob_dir", + "-blob_threshold", "-cachesize", "-cache_max", "-create", @@ -574,9 +589,11 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) TCL_ENV_LOCK, TCL_ENV_CONFLICT, TCL_ENV_DETECT, - TCL_ENV_LOCK_LOCKS, TCL_ENV_LOCK_LOCKERS, + TCL_ENV_LOCK_LOCKS, + TCL_ENV_LOCK_LOGID, TCL_ENV_LOCK_OBJECTS, + TCL_ENV_LOCK_THREAD, TCL_ENV_LOCK_MAX_LOCKS, TCL_ENV_LOCK_MAX_LOCKERS, TCL_ENV_LOCK_MAX_OBJECTS, @@ -585,6 +602,7 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) TCL_ENV_LOCK_TIMEOUT, TCL_ENV_LOG, TCL_ENV_LOG_FILEMODE, + TCL_ENV_LOG_BLOB, TCL_ENV_LOG_BUFFER, TCL_ENV_LOG_INMEMORY, TCL_ENV_LOG_MAX, @@ -597,6 +615,7 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) TCL_ENV_MUTEXCOUNT, TCL_ENV_MPOOL_NOMMAP, TCL_ENV_MULTIVERSION, + TCL_ENV_MUT_FAILCHK_TIMEOUT, TCL_ENV_MUTSETALIGN, TCL_ENV_MUTSETINCR, TCL_ENV_MUTSETINIT, @@ -609,11 +628,18 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) TCL_ENV_REGION_INIT, TCL_ENV_REP, TCL_ENV_REP_CLIENT, + TCL_ENV_REP_CONFIG, TCL_ENV_REP_INMEM_FILES, TCL_ENV_REP_LEASE, + TCL_ENV_REP_LIMIT, TCL_ENV_REP_MASTER, TCL_ENV_REP_NSITES, + TCL_ENV_REP_PRIORITY, + TCL_ENV_REP_REQUEST, + TCL_ENV_REP_TIMEOUT, TCL_ENV_REP_TRANSPORT, + TCL_ENV_REP_VIEW, + TCL_ENV_REPMGR_ACK_POLICY, TCL_ENV_SET_INTERMEDIATE_DIR, TCL_ENV_SNAPSHOT, TCL_ENV_TABLESIZE, @@ -628,6 +654,8 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) TCL_ENV_ZEROLOG, #endif TCL_ENV_ADD_DIR, + TCL_ENV_BLOB_DIR, + TCL_ENV_BLOB_THRESHOLD, TCL_ENV_CACHESIZE, TCL_ENV_CACHE_MAX, TCL_ENV_CREATE, @@ -875,9 +903,11 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), "lock_detect"); break; - case TCL_ENV_LOCK_LOCKS: case TCL_ENV_LOCK_LOCKERS: + case TCL_ENV_LOCK_LOCKS: + case TCL_ENV_LOCK_LOGID: case TCL_ENV_LOCK_OBJECTS: + case TCL_ENV_LOCK_THREAD: case TCL_ENV_LOCK_MAX_LOCKS: case TCL_ENV_LOCK_MAX_LOCKERS: case TCL_ENV_LOCK_MAX_OBJECTS: @@ -893,18 +923,26 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) if (result == TCL_OK) { _debug_check(); switch ((enum envopen)optindex) { + case TCL_ENV_LOCK_LOCKERS: + ret = dbenv->set_memory_init(dbenv, + DB_MEM_LOCKER, uintarg); + break; case TCL_ENV_LOCK_LOCKS: ret = dbenv->set_memory_init(dbenv, DB_MEM_LOCK, uintarg); break; - case TCL_ENV_LOCK_LOCKERS: + case TCL_ENV_LOCK_LOGID: ret = dbenv->set_memory_init(dbenv, - DB_MEM_LOCKER, uintarg); + DB_MEM_LOGID, uintarg); break; case TCL_ENV_LOCK_OBJECTS: ret = dbenv->set_memory_init(dbenv, DB_MEM_LOCKOBJECT, uintarg); break; + case TCL_ENV_LOCK_THREAD: + ret = dbenv->set_memory_init(dbenv, + DB_MEM_THREAD, uintarg); + break; case TCL_ENV_LOCK_MAX_LOCKS: ret = dbenv->set_lk_max_locks(dbenv, uintarg); @@ -971,6 +1009,7 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) case TCL_ENV_TXN_TIME: case TCL_ENV_TXN_TIMEOUT: case TCL_ENV_LOCK_TIMEOUT: + case TCL_ENV_MUT_FAILCHK_TIMEOUT: case TCL_ENV_REG_TIMEOUT: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, @@ -995,6 +1034,10 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) else if ((enum envopen)optindex == TCL_ENV_REG_TIMEOUT) time_flag = DB_SET_REG_TIMEOUT; + else if ((enum envopen)optindex == + TCL_ENV_MUT_FAILCHK_TIMEOUT) + time_flag = + DB_SET_MUTEX_FAILCHK_TIMEOUT; else time_flag = DB_SET_TXN_TIMEOUT; @@ -1007,6 +1050,12 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) case TCL_ENV_LOG: FLD_SET(open_flags, DB_INIT_LOG | DB_INIT_MPOOL); break; + case TCL_ENV_LOG_BLOB: + ret = + dbenv->log_set_config(dbenv, DB_LOG_BLOB, 1); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "log_blob"); + break; case TCL_ENV_LOG_BUFFER: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, @@ -1061,15 +1110,8 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) result = TCL_ERROR; break; } - result = _GetUInt32(interp, objv[i++], &uintarg); - if (result == TCL_OK && logbufset) { - _debug_check(); - ret = dbenv->set_lg_max(dbenv, uintarg); - result = _ReturnSetup(interp, ret, - DB_RETOK_STD(ret), "log_max"); - logbufset = 0; - } else - logmaxset = uintarg; + result = tcl_LogSetMax( + interp, dbenv, objv[i++], &logbufset, &logmaxset); break; case TCL_ENV_LOG_REGIONMAX: if (i >= objc) { @@ -1259,6 +1301,58 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) rep_flags = DB_REP_CLIENT; FLD_SET(open_flags, DB_INIT_REP); break; + case TCL_ENV_REP_CONFIG: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-rep_config {which onoff}"); + result = TCL_ERROR; + break; + } + result = tcl_RepConfig(interp, dbenv, objv[i]); + if (result == TCL_OK) { + i++; + FLD_SET(open_flags, DB_INIT_REP); + } + break; + case TCL_ENV_REP_INMEM_FILES: + result = tcl_RepInmemFiles(interp,dbenv); + if (result == TCL_OK) + FLD_SET(open_flags, DB_INIT_REP); + break; + case TCL_ENV_REP_LEASE: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-rep_lease {timeout clockskew}"); + result = TCL_ERROR; + break; + } + result = Tcl_ListObjGetElements(interp, objv[i], + &myobjc, &myobjv); + if (result == TCL_OK) + i++; + else + break; + result = tcl_RepLease(interp, myobjc, myobjv, dbenv); + if (result == TCL_OK) + FLD_SET(open_flags, DB_INIT_REP); + break; + case TCL_ENV_REP_LIMIT: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-rep_limit {gbytes bytes}"); + result = TCL_ERROR; + break; + } + result = Tcl_ListObjGetElements(interp, objv[i], + &myobjc, &myobjv); + if (result == TCL_OK) + i++; + else + break; + result = tcl_RepLimit(interp, myobjc, myobjv, dbenv); + if (result == TCL_OK) + FLD_SET(open_flags, DB_INIT_REP); + break; case TCL_ENV_REP_MASTER: rep_flags = DB_REP_MASTER; FLD_SET(open_flags, DB_INIT_REP); @@ -1280,15 +1374,27 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) if (result == TCL_OK) FLD_SET(open_flags, DB_INIT_REP); break; - case TCL_ENV_REP_INMEM_FILES: - result = tcl_RepInmemFiles(interp,dbenv); + case TCL_ENV_REP_PRIORITY: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-rep_priority priority"); + result = TCL_ERROR; + break; + } + result = _GetUInt32(interp, objv[i++], &uintarg); + if (result == TCL_OK) { + _debug_check(); + ret = dbenv->rep_set_priority(dbenv, uintarg); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "rep_set_priority"); + } if (result == TCL_OK) FLD_SET(open_flags, DB_INIT_REP); break; - case TCL_ENV_REP_LEASE: + case TCL_ENV_REP_REQUEST: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, - "-rep_lease {timeout clockskew}"); + "-rep_request {minTime maxTime}"); result = TCL_ERROR; break; } @@ -1298,7 +1404,31 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) i++; else break; - result = tcl_RepLease(interp, myobjc, myobjv, dbenv); + result = tcl_RepRequest(interp, myobjc, myobjv, dbenv); + if (result == TCL_OK) + FLD_SET(open_flags, DB_INIT_REP); + break; + case TCL_ENV_REP_TIMEOUT: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-rep_timout {which timeout}"); + result = TCL_ERROR; + break; + } + if ((result = Tcl_ListObjGetElements(interp, objv[i], + &myobjc, &myobjv)) != TCL_OK ) + break; + _debug_check(); + if ((result = + Tcl_GetIntFromObj(interp, myobjv[0], &intarg)) != TCL_OK) + break; + if ((result = + _GetUInt32(interp, myobjv[1], &uintarg)) != TCL_OK) + break; + i++; + ret = dbenv->rep_set_timeout(dbenv, intarg, uintarg); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "rep_set_timeout"); if (result == TCL_OK) FLD_SET(open_flags, DB_INIT_REP); break; @@ -1320,6 +1450,56 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) if (result == TCL_OK) FLD_SET(open_flags, DB_INIT_REP); break; + case TCL_ENV_REP_VIEW: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-rep_view {viewproc}"); + result = TCL_ERROR; + break; + } + + /* + * We use a list here instead of just sending in the + * proc name so that an empty list can indicate to + * use the BDB default full view and we send in NULL. + */ + result = Tcl_ListObjGetElements(interp, objv[i], + &myobjc, &myobjv); + if (result == TCL_OK) + i++; + else + break; + if (myobjc == 0) { + ip->i_rep_view = NULL; + _debug_check(); + ret = dbenv->rep_set_view(dbenv, NULL); + } else { + ip->i_rep_view = myobjv[0]; + Tcl_IncrRefCount(ip->i_rep_view); + _debug_check(); + ret = dbenv->rep_set_view(dbenv, tcl_rep_view); + } + result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), + "rep_set_view"); + break; + case TCL_ENV_REPMGR_ACK_POLICY: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-rep_ack_policy {ack_policy}"); + result = TCL_ERROR; + break; + } + result = Tcl_GetIntFromObj(interp, objv[i++], &intarg); + if (result == TCL_OK) { + _debug_check(); + ret = dbenv-> + repmgr_set_ack_policy(dbenv, intarg); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "repmgr_set_ack_policy"); + } + if (result == TCL_OK) + FLD_SET(open_flags, DB_INIT_REP); + break; case TCL_ENV_SNAPSHOT: FLD_SET(set_flags, DB_TXN_SNAPSHOT); break; @@ -1464,7 +1644,29 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) case TCL_ENV_USE_ENVIRON: FLD_SET(open_flags, DB_USE_ENVIRON); break; + case TCL_ENV_BLOB_THRESHOLD: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-blob_threshold bytes?"); + result = TCL_ERROR; + break; + } + result = _GetUInt32(interp, objv[i++], &bytes); + if (result == TCL_OK) { + _debug_check(); + ret = dbenv->set_blob_threshold(dbenv, + bytes, 0); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "set_blob_threshold"); + } + break; case TCL_ENV_CACHESIZE: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-cachesize {gbytes bytes ncaches}?"); + result = TCL_ERROR; + break; + } result = Tcl_ListObjGetElements(interp, objv[i], &myobjc, &myobjv); if (result == TCL_OK) @@ -1580,8 +1782,8 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) break; } arg = Tcl_GetStringFromObj(objv[i++], NULL); - tcl_EnvSetMsgfile(interp, dbenv, ip, arg); - break; + result = tcl_EnvSetMsgfile(interp, dbenv, ip, arg); + break; case TCL_ENV_ERRPFX: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, @@ -1593,9 +1795,10 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) _debug_check(); result = tcl_EnvSetErrpfx(interp, dbenv, ip, arg); break; - case TCL_ENV_DATA_DIR: case TCL_ENV_ADD_DIR: + case TCL_ENV_BLOB_DIR: case TCL_ENV_CREATE_DIR: + case TCL_ENV_DATA_DIR: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, "-xxx_dir dir"); @@ -1605,15 +1808,18 @@ bdb_EnvOpen(interp, objc, objv, ip, dbenvp) arg = Tcl_GetStringFromObj(objv[i++], NULL); _debug_check(); switch ((enum envopen)optindex) { - case TCL_ENV_DATA_DIR: - ret = dbenv->set_data_dir(dbenv, arg); - break; case TCL_ENV_ADD_DIR: ret = dbenv->add_data_dir(dbenv, arg); break; + case TCL_ENV_BLOB_DIR: + ret = dbenv->set_blob_dir(dbenv, arg); + break; case TCL_ENV_CREATE_DIR: ret = dbenv->set_create_dir(dbenv, arg); break; + case TCL_ENV_DATA_DIR: + ret = dbenv->set_data_dir(dbenv, arg); + break; default: break; } @@ -1785,6 +1991,8 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) "-thread", #endif "-auto_commit", + "-blob_dir", + "-blob_threshold", "-btree", "-cachesize", "-chksum", @@ -1806,6 +2014,7 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) "-hash", "-heap", "-heap_regionsize", + "-heapsize", "-inorder", "-len", "-lk_exclusive", @@ -1848,6 +2057,8 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) TCL_DB_THREAD, #endif TCL_DB_AUTO_COMMIT, + TCL_DB_BLOB_DIR, + TCL_DB_BLOB_THRESHOLD, TCL_DB_BTREE, TCL_DB_CACHESIZE, TCL_DB_CHKSUM, @@ -1869,6 +2080,7 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) TCL_DB_HASH, TCL_DB_HEAP, TCL_DB_HEAP_REGIONSIZE, + TCL_DB_HEAPSIZE, TCL_DB_INORDER, TCL_DB_LEN, TCL_DB_LK_EXCLUSIVE, @@ -1908,7 +2120,8 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) size_t nlen; type = DB_UNKNOWN; - endarg = encenble = mode = nlen = set_err = set_msg = set_flags = 0; + endarg = encenble = mode = set_err = set_msg = set_flags = 0; + nlen = 0; set_pfx = 0; result = TCL_OK; subdbtmp = NULL; @@ -2122,6 +2335,34 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) DB_RETOK_STD(ret), "set_heap_regionsize"); } break; + case TCL_DB_HEAPSIZE: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-heapsize {gbytes bytes}?"); + result = TCL_ERROR; + break; + } + result = Tcl_ListObjGetElements(interp, objv[i++], + &myobjc, &myobjv); + if (result != TCL_OK) + break; + if (myobjc != 2) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-heapsize {gbytes bytes}?"); + result = TCL_ERROR; + break; + } + result = _GetUInt32(interp, myobjv[0], &gbytes); + if (result != TCL_OK) + break; + result = _GetUInt32(interp, myobjv[1], &bytes); + if (result != TCL_OK) + break; + _debug_check(); + ret = (*dbp)->set_heapsize(*dbp, gbytes, bytes, 0); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "set_heapsize"); + break; case TCL_DB_LORDER: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, @@ -2533,6 +2774,37 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) DB_RETOK_STD(ret), "set_q_extentsize"); } break; + case TCL_DB_BLOB_DIR: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-blob_threshold dir?"); + result = TCL_ERROR; + break; + } + arg = Tcl_GetStringFromObj(objv[i++], NULL); + if (arg != NULL && strlen(arg) != 0) { + _debug_check(); + ret = (*dbp)->set_blob_dir(*dbp, arg); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "set_blob_dir"); + } + break; + case TCL_DB_BLOB_THRESHOLD: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-blob_threshold bytes?"); + result = TCL_ERROR; + break; + } + result = _GetUInt32(interp, objv[i++], &bytes); + if (result == TCL_OK) { + _debug_check(); + ret = (*dbp)->set_blob_threshold(*dbp, + bytes, 0); + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "set_blob_threshold"); + } + break; case TCL_DB_CACHESIZE: result = Tcl_ListObjGetElements(interp, objv[i++], &myobjc, &myobjv); @@ -2615,18 +2887,22 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) if (errip->i_msg != NULL && errip->i_msg != stdout && errip->i_msg != stderr) (void)fclose(errip->i_msg); - if (strcmp(arg, "/dev/stdout") == 0) + if (strcmp(arg, "NULL") == 0) + errip->i_msg = NULL; + else if (strcmp(arg, "/dev/stdout") == 0) errip->i_msg = stdout; else if (strcmp(arg, "/dev/stderr") == 0) errip->i_msg = stderr; else errip->i_msg = fopen(arg, "a"); - if (errip->i_msg != NULL) { + if (strcmp(arg, "NULL") == 0 || errip->i_msg != NULL) { _debug_check(); (*dbp)->set_msgfile(*dbp, errip->i_msg); set_msg = 1; } - break; + else + set_msg = 0; + break; case TCL_DB_ERRPFX: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, @@ -2818,7 +3094,9 @@ bdb_DbOpen(interp, objc, objv, ip, dbp) dbr[nlen] = '2'; if (subdbr != NULL) subdbr[nlen] = '2'; - + + /* Disable blobs in case they are enabled environment wide. */ + (void)hsdbp->set_blob_threshold(hsdbp, 0, 0); /* * Use same flags as heap, note: heap does not use of * DB_AFTER/DB_BEFORE on cursor puts, but recno can. @@ -2968,8 +3246,8 @@ bdb_SeqOpen(interp, objc, objv, ip, seqp) db_recno_t recno; db_seq_t min, max, value; Tcl_WideInt tcl_value; - u_int32_t flags, oflags; - int cache, endarg, i, optindex, result, ret, setrange, setvalue, v; + u_int32_t cache, flags, oflags; + int endarg, i, optindex, result, ret, setrange, setvalue, v; char *arg, *db, msg[MSG_SIZE]; COMPQUIET(ip, NULL); @@ -3017,7 +3295,7 @@ bdb_SeqOpen(interp, objc, objv, ip, seqp) result = TCL_ERROR; break; } - result = Tcl_GetIntFromObj(interp, objv[i++], &cache); + result = _GetUInt32(interp, objv[i++], &cache); break; case TCL_SEQ_INIT: if (i >= objc) { @@ -3175,6 +3453,7 @@ bdb_DbRemove(interp, objc, objv) { static const char *bdbrem[] = { "-auto_commit", + "-blob_dir", "-encrypt", "-encryptaes", "-encryptany", @@ -3186,6 +3465,7 @@ bdb_DbRemove(interp, objc, objv) }; enum bdbrem { TCL_DBREM_AUTOCOMMIT, + TCL_DBREM_BLOBDIR, TCL_DBREM_ENCRYPT, TCL_DBREM_ENCRYPT_AES, TCL_DBREM_ENCRYPT_ANY, @@ -3201,18 +3481,19 @@ bdb_DbRemove(interp, objc, objv) u_int32_t enc_flag, iflags, set_flags; int endarg, i, optindex, result, ret, subdblen; u_char *subdbtmp; - char *arg, *db, *dbr, msg[MSG_SIZE], *passwd, *subdb, *subdbr; + char *arg, *bdir, *db, *dbr, msg[MSG_SIZE], *passwd, *subdb, *subdbr; size_t nlen; dbp = NULL; dbenv = NULL; txn = NULL; env = NULL; - enc_flag = iflags = set_flags = subdblen = 0; - endarg = nlen = 0; + enc_flag = iflags = set_flags = 0; + endarg = subdblen = 0; + nlen = 0; result = TCL_OK; subdbtmp = NULL; - db = dbr = passwd = subdb = subdbr = NULL; + bdir = db = dbr = passwd = subdb = subdbr = NULL; if (objc < 2) { Tcl_WrongNumArgs(interp, 2, objv, "?args? filename ?database?"); @@ -3241,6 +3522,16 @@ bdb_DbRemove(interp, objc, objv) iflags |= DB_AUTO_COMMIT; _debug_check(); break; + case TCL_DBREM_BLOBDIR: + /* Make sure we have an arg to check against! */ + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-blob_dir dir?"); + result = TCL_ERROR; + break; + } + bdir = Tcl_GetStringFromObj(objv[i++], NULL); + break; case TCL_DBREM_ENCRYPT: set_flags |= DB_ENCRYPT; _debug_check(); @@ -3372,6 +3663,14 @@ bdb_DbRemove(interp, objc, objv) result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), "set_flags"); } + + if (bdir != NULL) { + ret = dbp->set_blob_dir(dbp, bdir); + result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), + "set_blob_dir"); + if (ret != 0) + goto error; + } } /* @@ -3922,6 +4221,7 @@ bdb_DbVerify(interp, objc, objv, ip) DBTCL_INFO *ip; /* Our internal info */ { static const char *bdbverify[] = { + "-blob_dir", "-btcompare", "-dupcompare", "-hashcompare", @@ -3940,6 +4240,7 @@ bdb_DbVerify(interp, objc, objv, ip) NULL }; enum bdbvrfy { + TCL_DBVRFY_BLOBDIR, TCL_DBVRFY_BTCOMPARE, TCL_DBVRFY_DUPCOMPARE, TCL_DBVRFY_HASHCOMPARE, @@ -3959,20 +4260,20 @@ bdb_DbVerify(interp, objc, objv, ip) DB_ENV *dbenv; DB *dbp; FILE *errf; - int (*bt_compare) __P((DB *, const DBT *, const DBT *)); - int (*dup_compare) __P((DB *, const DBT *, const DBT *)); - int (*h_compare) __P((DB *, const DBT *, const DBT *)); + int (*bt_compare) __P((DB *, const DBT *, const DBT *, size_t *)); + int (*dup_compare) __P((DB *, const DBT *, const DBT *, size_t *)); + int (*h_compare) __P((DB *, const DBT *, const DBT *, size_t *)); u_int32_t (*h_hash)__P((DB *, const void *, u_int32_t)); u_int32_t enc_flag, flags, set_flags; int endarg, i, optindex, result, ret, subdblen; - char *arg, *db, *errpfx, *passwd, *subdb; + char *arg, *bldir, *db, *errpfx, *passwd, *subdb; u_char *subdbtmp; dbenv = NULL; dbp = NULL; passwd = NULL; result = TCL_OK; - db = errpfx = subdb = NULL; + bldir = db = errpfx = subdb = NULL; errf = NULL; bt_compare = NULL; dup_compare = NULL; @@ -4004,6 +4305,27 @@ bdb_DbVerify(interp, objc, objv, ip) } i++; switch ((enum bdbvrfy)optindex) { + case TCL_DBVRFY_BLOBDIR: + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "-blobdir dir"); + result = TCL_ERROR; + break; + } + arg = Tcl_GetStringFromObj(objv[i++], NULL); + /* + * If the user already set one, free it. + */ + if (bldir != NULL) + __os_free(dbenv != NULL ? + dbenv->env : NULL, bldir); + if ((ret = __os_strdup(NULL, arg, &bldir)) != 0) { + result = _ReturnSetup(interp, ret, + DB_RETOK_STD(ret), "__os_strdup"); + break; + } + _debug_check(); + break; case TCL_DBVRFY_BTCOMPARE: if (i >= objc) { Tcl_WrongNumArgs(interp, 2, objv, @@ -4222,6 +4544,13 @@ bdb_DbVerify(interp, objc, objv, ip) /* Hang our info pointer on the DB handle, so we can do callbacks. */ dbp->api_internal = ip; + if (bldir != NULL && dbenv == NULL && + (ret = dbp->set_blob_dir(dbp, bldir)) != 0) { + result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), + "set_blob_dir"); + goto error; + } + if (errf != NULL) dbp->set_errfile(dbp, errf); if (errpfx != NULL) @@ -4272,6 +4601,8 @@ bdb_DbVerify(interp, objc, objv, ip) result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), "db verify"); dbp = NULL; error: + if (bldir != NULL) + __os_free(dbenv != NULL ? dbenv->env : NULL, bldir); if (errf != NULL && errf != stdout && errf != stderr) (void)fclose(errf); if (errpfx != NULL) @@ -4405,6 +4736,9 @@ bdb_GetConfig(interp, objc, objv) #ifdef DIAGNOSTIC ADD_CONFIG_NAME("diagnostic"); #endif +#ifdef HAVE_FAILCHK_BROADCAST + ADD_CONFIG_NAME("failchk_broadcast"); +#endif #ifdef HAVE_PARTITION ADD_CONFIG_NAME("partition"); #endif @@ -4484,8 +4818,9 @@ bdb_MsgType(interp, objc, objv) * Add "no_type" for 0 so that we directly index. */ static const char *msgnames[] = { - "no_type", "alive", "alive_req", "all_req", - "bulk_log", "bulk_page", + "no_type", "alive", "alive_req", "all_req", "blob_all_req", + "blob_chunk", "blob_chunk_req", "blob_update", + "blob_update_req", "bulk_log", "bulk_page", "dupmaster", "file", "file_fail", "file_req", "lease_grant", "log", "log_more", "log_req", "master_req", "newclient", "newfile", "newmaster", "newsite", "page", @@ -4535,23 +4870,27 @@ bdb_DbUpgrade(interp, objc, objv) Tcl_Obj *CONST objv[]; /* The argument objects */ { static const char *bdbupg[] = { - "-dupsort", "-env", "--", NULL + "-dupsort", "-env", "-P", "--", NULL }; enum bdbupg { TCL_DBUPG_DUPSORT, TCL_DBUPG_ENV, + TCL_DBUPG_PASSWORD, TCL_DBUPG_ENDARG }; DB_ENV *dbenv; DB *dbp; + ENV *env; u_int32_t flags; int endarg, i, optindex, result, ret; - char *arg, *db; + char *arg, *db, *dbr, *passwd; + size_t nlen; dbenv = NULL; dbp = NULL; + env = NULL; result = TCL_OK; - db = NULL; + db = dbr = passwd = NULL; flags = endarg = 0; if (objc < 2) { @@ -4585,6 +4924,16 @@ bdb_DbUpgrade(interp, objc, objv) TCL_STATIC); return (TCL_ERROR); } + env = dbenv->env; + break; + case TCL_DBUPG_PASSWORD: + /* Make sure we have an arg to check against! */ + if (i >= objc) { + Tcl_WrongNumArgs(interp, 2, objv, + "?-P passwd?"); + return (TCL_ERROR); + } + passwd = Tcl_GetStringFromObj(objv[i++], NULL); break; case TCL_DBUPG_ENDARG: endarg = 1; @@ -4630,11 +4979,40 @@ bdb_DbUpgrade(interp, objc, objv) dbp->set_errpfx(dbp, "DbUpgrade"); dbp->set_errcall(dbp, _ErrorFunc); } + if (passwd != NULL) { + if ((ret = dbp->set_encrypt( + dbp, passwd, DB_ENCRYPT_AES)) != 0 ) { + result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), + "set_encrypt"); + goto error; + } + } ret = dbp->upgrade(dbp, db, flags); - result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), "db upgrade"); + + if (ret == 0 && db != NULL) { + nlen = strlen(db); + if ((ret = __os_malloc(env, nlen + 2, &dbr)) != 0) { + Tcl_SetResult(interp, db_strerror(ret), + TCL_STATIC); + return (0); + } + memcpy(dbr, db, nlen); + dbr[nlen] = '1'; + dbr[nlen+1] = '\0'; + /* If the associated heap databases exist, upgrade them. */ + if (__os_exists(env, dbr, NULL) == 0) { + if ((ret = dbp->upgrade(dbp, dbr, flags)) != 0) + goto end; + dbr[nlen] = '2'; + ret = dbp->upgrade(dbp, dbr, flags); + } + } +end: result = _ReturnSetup(interp, ret, DB_RETOK_STD(ret), "db upgrade"); error: if (dbp) (void)dbp->close(dbp, 0); + if (dbr) + __os_free(env, dbr); return (result); } @@ -4645,19 +5023,23 @@ error: * reporting and the Tcl_Obj representing their respective procs. */ static int -tcl_bt_compare(dbp, dbta, dbtb) +tcl_bt_compare(dbp, dbta, dbtb, locp) DB *dbp; const DBT *dbta, *dbtb; + size_t *locp; { + COMPQUIET(locp, NULL); return (tcl_compare_callback(dbp, dbta, dbtb, ((DBTCL_INFO *)dbp->api_internal)->i_compare, "bt_compare")); } static int -tcl_dup_compare(dbp, dbta, dbtb) +tcl_dup_compare(dbp, dbta, dbtb, locp) DB *dbp; const DBT *dbta, *dbtb; + size_t *locp; { + COMPQUIET(locp, NULL); return (tcl_compare_callback(dbp, dbta, dbtb, ((DBTCL_INFO *)dbp->api_internal)->i_dupcompare, "dup_compare")); } @@ -4771,6 +5153,10 @@ err: __db_errx(dbp->env, "Tcl h_hash callback failed"); return (0); } +/* + * We only support testing that the process is alive for now, because that + * seems easiest, and that's all we need for our tests for the moment. + */ static int tcl_isalive(dbenv, pid, tid, flags) DB_ENV *dbenv; @@ -4790,12 +5176,6 @@ tcl_isalive(dbenv, pid, tid, flags) if (mypid == pid && (LF_ISSET(DB_MUTEX_PROCESS_ONLY) || mytid == tid)) return (1); - /* - * We only support the PROCESS_ONLY case for now, because that seems - * easiest, and that's all we need for our tests for the moment. - */ - if (!LF_ISSET(DB_MUTEX_PROCESS_ONLY)) - return (1); ip = (DBTCL_INFO *)dbenv->app_private; interp = ip->i_interp; @@ -4971,6 +5351,64 @@ err: __db_errx(dbenv->env, return (ret); } + +static int +tcl_rep_view(dbenv, name, result, flags) + DB_ENV *dbenv; + const char *name; + int *result; + u_int32_t flags; +{ +#define TCLDB_VIEWITEMS 3 + ENV *env; + DBTCL_INFO *ip; + Tcl_Interp *interp; + Tcl_Obj *flags_o, *myobjv[TCLDB_MAXREPFLAGS], *objv[TCLDB_VIEWITEMS]; + int i, myobjc, res; + + COMPQUIET(flags, 0); + ip = (DBTCL_INFO *)dbenv->app_private; + interp = ip->i_interp; + myobjv[myobjc = 0] = NULL; + if (flags == 0) + myobjv[myobjc++] = NewStringObj("none", strlen("none")); + /* + * If we're given an unrecognized flag send "unknown". + */ + if (myobjc == 0) + myobjv[myobjc++] = NewStringObj("unknown", strlen("unknown")); + for (i = 0; i < myobjc; i++) + Tcl_IncrRefCount(myobjv[i]); + flags_o = Tcl_NewListObj(myobjc, myobjv); + + objv[0] = ip->i_rep_view; + objv[1] = NewStringObj(name, strlen(name)); + objv[2] = flags_o; /* Flags */ + Tcl_IncrRefCount(objv[1]); + Tcl_IncrRefCount(flags_o); + + res = Tcl_EvalObjv(interp, TCLDB_VIEWITEMS, objv, 0); + if (res != TCL_OK) + goto err; + Tcl_DecrRefCount(objv[1]); + for (i = 0; i < myobjc; i++) + Tcl_DecrRefCount(myobjv[i]); + Tcl_DecrRefCount(flags_o); + /* + * Put the result "do we replicate or not" into 'result'. + */ + res = Tcl_GetIntFromObj(interp, Tcl_GetObjResult(interp), result); + if (res != TCL_OK) + goto err; + + return (0); + +err: env = dbenv->env; + __db_errx(env, "Tcl rep_view callback failed: %s", + Tcl_GetStringResult(interp)); + + return (1); +} #endif #ifdef CONFIG_TEST @@ -4994,7 +5432,7 @@ tcl_db_malloc(size) Tcl_SetObjLength(obj, (int)(size + sizeof(Tcl_Obj *))); buf = Tcl_GetString(obj); - memcpy(buf, &obj, sizeof(&obj)); + memcpy(buf, &obj, sizeof(Tcl_Obj *)); buf = (Tcl_Obj **)buf + 1; return (buf); @@ -5014,7 +5452,7 @@ tcl_db_realloc(ptr, size) Tcl_SetObjLength(obj, (int)(size + sizeof(Tcl_Obj *))); ptr = Tcl_GetString(obj); - memcpy(ptr, &obj, sizeof(&obj)); + memcpy(ptr, &obj, sizeof(Tcl_Obj *)); ptr = (Tcl_Obj **)ptr + 1; return (ptr); |