diff options
Diffstat (limited to 'db/build_win32/db_int.h')
-rw-r--r-- | db/build_win32/db_int.h | 366 |
1 files changed, 226 insertions, 140 deletions
diff --git a/db/build_win32/db_int.h b/db/build_win32/db_int.h index 0eb4309fc..c6daf139b 100644 --- a/db/build_win32/db_int.h +++ b/db/build_win32/db_int.h @@ -2,22 +2,21 @@ /*- * See the file LICENSE for redistribution information. * - * Copyright (c) 1996, 1997, 1998, 1999, 2000 + * Copyright (c) 1996-2003 * Sleepycat Software. All rights reserved. * - * $Id: db_int.src,v 11.42 2001/01/11 17:49:17 krinsky Exp $ + * $Id: db_int.in,v 11.126 2003/09/10 17:27:14 sue Exp $ */ #ifndef _DB_INTERNAL_H_ #define _DB_INTERNAL_H_ /******************************************************* - * General includes. + * System includes, db.h, a few general DB includes. The DB includes are + * here because it's OK if db_int.h includes queue structure declarations. *******************************************************/ -#include "db.h" - #ifndef NO_SYSTEM_INCLUDES -#if defined(__STDC__) || defined(__cplusplus) +#if defined(STDC_HEADERS) || defined(__cplusplus) #include <stdarg.h> #else #include <varargs.h> @@ -25,8 +24,10 @@ #include <errno.h> #endif -#include "queue.h" -#include "shqueue.h" +#include "db.h" + +#include "dbinc/queue.h" +#include "dbinc/shqueue.h" #if defined(__cplusplus) extern "C" { @@ -44,10 +45,19 @@ extern "C" { #define MS_PER_SEC 1000 /* Milliseconds in a second. */ #define USEC_PER_MS 1000 /* Microseconds in a millisecond. */ +#define RECNO_OOB 0 /* Illegal record number. */ + +/* Test for a power-of-two (tests true for zero, which doesn't matter here). */ +#define POWER_OF_TWO(x) (((x) & ((x) - 1)) == 0) + +/* Test for valid page sizes. */ #define DB_MIN_PGSIZE 0x000200 /* Minimum page size (512). */ #define DB_MAX_PGSIZE 0x010000 /* Maximum page size (65536). */ +#define IS_VALID_PAGESIZE(x) \ + (POWER_OF_TWO(x) && (x) >= DB_MIN_PGSIZE && ((x) <= DB_MAX_PGSIZE)) -#define RECNO_OOB 0 /* Illegal record number. */ +/* Minimum number of pages cached, by default. */ +#define DB_MINPAGECACHE 16 /* * If we are unable to determine the underlying filesystem block size, use @@ -55,6 +65,9 @@ extern "C" { */ #define DB_DEF_IOSIZE (8 * 1024) +/* Number of times to reties I/O operations that return EINTR or EBUSY. */ +#define DB_RETRY 100 + /* * Aligning items to particular sizes or in pages or memory. * @@ -80,12 +93,25 @@ typedef unsigned long db_alignp_t; /* Align an integer to a specific boundary. */ #undef ALIGN -#define ALIGN(value, bound) \ - (((value) + (bound) - 1) & ~(((u_int)bound) - 1)) +#define ALIGN(v, bound) (((v) + (bound) - 1) & ~(((db_align_t)bound) - 1)) -/* Align a pointer to a specific boundary. */ -#undef ALIGNP -#define ALIGNP(value, bound) ALIGN((db_alignp_t)value, bound) +/* + * Print an address as a u_long (a u_long is the largest type we can print + * portably). Most 64-bit systems have made longs 64-bits, so this should + * work. + */ +#define P_TO_ULONG(p) ((u_long)(db_alignp_t)(p)) + +/* + * Convert a pointer to a small integral value. + * + * The (u_int16_t)(db_alignp_t) cast avoids warnings: the (db_alignp_t) cast + * converts the value to an integral type, and the (u_int16_t) cast converts + * it to a small integral type so we don't get complaints when we assign the + * final result to an integral type smaller than db_alignp_t. + */ +#define P_TO_UINT32(p) ((u_int32_t)(db_alignp_t)(p)) +#define P_TO_UINT16(p) ((u_int16_t)(db_alignp_t)(p)) /* * There are several on-page structures that are declared to have a number of @@ -101,17 +127,10 @@ typedef unsigned long db_alignp_t; * an array. */ #undef SSZ -#define SSZ(name, field) ((int)&(((name *)0)->field)) +#define SSZ(name, field) P_TO_UINT16(&(((name *)0)->field)) #undef SSZA -#define SSZA(name, field) ((int)&(((name *)0)->field[0])) - -/* - * Print an address as a u_long (a u_long is the largest type we can print - * portably). Most 64-bit systems have made longs 64-bits, so this should - * work. - */ -#define P_TO_ULONG(p) ((u_long)(db_alignp_t)(p)) +#define SSZA(name, field) P_TO_UINT16(&(((name *)0)->field[0])) /* Structure used to print flag values. */ typedef struct __fn { @@ -126,51 +145,65 @@ typedef struct __fn { #define F_CLR(p, f) (p)->flags &= ~(f) #define F_ISSET(p, f) ((p)->flags & (f)) #define F_SET(p, f) (p)->flags |= (f) -#define LF_CLR(f) (flags &= ~(f)) -#define LF_ISSET(f) (flags & (f)) -#define LF_SET(f) (flags |= (f)) +#define LF_CLR(f) ((flags) &= ~(f)) +#define LF_ISSET(f) ((flags) & (f)) +#define LF_SET(f) ((flags) |= (f)) /* Display separator string. */ #undef DB_LINE #define DB_LINE "=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=" -/* Unused, or not-used-yet variable. "Shut that bloody compiler up!" */ -#define COMPQUIET(n, v) (n) = (v) +/******************************************************* + * API return values + *******************************************************/ +/* + * Return values that are OK for each different call. Most calls have a + * standard 'return of 0 is only OK value', but some, like db->get have + * DB_NOTFOUND as a return value, but it really isn't an error. + */ +#define DB_RETOK_STD(ret) ((ret) == 0) +#define DB_RETOK_DBCDEL(ret) ((ret) == 0 || (ret) == DB_KEYEMPTY || \ + (ret) == DB_NOTFOUND) +#define DB_RETOK_DBCGET(ret) ((ret) == 0 || (ret) == DB_KEYEMPTY || \ + (ret) == DB_NOTFOUND) +#define DB_RETOK_DBCPUT(ret) ((ret) == 0 || (ret) == DB_KEYEXIST || \ + (ret) == DB_NOTFOUND) +#define DB_RETOK_DBDEL(ret) DB_RETOK_DBCDEL(ret) +#define DB_RETOK_DBGET(ret) DB_RETOK_DBCGET(ret) +#define DB_RETOK_DBPUT(ret) ((ret) == 0 || (ret) == DB_KEYEXIST) +#define DB_RETOK_LGGET(ret) ((ret) == 0 || (ret) == DB_NOTFOUND) +#define DB_RETOK_MPGET(ret) ((ret) == 0 || (ret) == DB_PAGE_NOTFOUND) +#define DB_RETOK_REPPMSG(ret) ((ret) == 0 || \ + (ret) == DB_REP_ISPERM || \ + (ret) == DB_REP_NEWMASTER || \ + (ret) == DB_REP_NEWSITE || \ + (ret) == DB_REP_NOTPERM) + +/* Find a reasonable operation-not-supported error. */ +#ifdef EOPNOTSUPP +#define DB_OPNOTSUP EOPNOTSUPP +#else +#ifdef ENOTSUP +#define DB_OPNOTSUP ENOTSUP +#else +#define DB_OPNOTSUP EINVAL +#endif +#endif /******************************************************* * Files. *******************************************************/ - /* - * We use 1024 as the maximum path length. It's too hard to figure out what - * the real path length is, as it was traditionally stored in <sys/param.h>, - * and that file isn't always available. - */ +/* + * We use 1024 as the maximum path length. It's too hard to figure out what + * the real path length is, as it was traditionally stored in <sys/param.h>, + * and that file isn't always available. + */ #undef MAXPATHLEN #define MAXPATHLEN 1024 #define PATH_DOT "." /* Current working directory. */ -#define PATH_SEPARATOR "\\/:" /* Path separator character. */ - -/* - * Flags understood by __os_open. - */ -#define DB_OSO_CREATE 0x001 /* POSIX: O_CREAT */ -#define DB_OSO_EXCL 0x002 /* POSIX: O_EXCL */ -#define DB_OSO_LOG 0x004 /* Opening a log file. */ -#define DB_OSO_RDONLY 0x008 /* POSIX: O_RDONLY */ -#define DB_OSO_REGION 0x010 /* Opening a region file. */ -#define DB_OSO_SEQ 0x020 /* Expected sequential access. */ -#define DB_OSO_TEMP 0x040 /* Remove after last close. */ -#define DB_OSO_TRUNC 0x080 /* POSIX: O_TRUNC */ - -/* - * Seek options understood by __os_seek. - */ -typedef enum { - DB_OS_SEEK_CUR, /* POSIX: SEEK_CUR */ - DB_OS_SEEK_END, /* POSIX: SEEK_END */ - DB_OS_SEEK_SET /* POSIX: SEEK_SET */ -} DB_OS_SEEK; + /* Path separator character(s). */ +#define PATH_SEPARATOR "\\/:" /******************************************************* * Environment. @@ -185,15 +218,21 @@ typedef enum { /* * CDB_LOCKING CDB product locking. + * CRYPTO_ON Security has been configured. * LOCKING_ON Locking has been configured. * LOGGING_ON Logging has been configured. * MPOOL_ON Memory pool has been configured. + * REP_ON Replication has been configured. + * RPC_ON RPC has been configured. * TXN_ON Transactions have been configured. */ #define CDB_LOCKING(dbenv) F_ISSET(dbenv, DB_ENV_CDB) +#define CRYPTO_ON(dbenv) ((dbenv)->crypto_handle != NULL) #define LOCKING_ON(dbenv) ((dbenv)->lk_handle != NULL) #define LOGGING_ON(dbenv) ((dbenv)->lg_handle != NULL) #define MPOOL_ON(dbenv) ((dbenv)->mp_handle != NULL) +#define REP_ON(dbenv) ((dbenv)->rep_handle != NULL) +#define RPC_ON(dbenv) ((dbenv)->cl_handle != NULL) #define TXN_ON(dbenv) ((dbenv)->tx_handle != NULL) /* @@ -206,21 +245,24 @@ typedef enum { !CDB_LOCKING((dbc)->dbp->dbenv) && LOCKING_ON((dbc)->dbp->dbenv)) /* - * IS_RECOVERING The system is running recovery. + * IS_RECOVERING: The system is running recovery. */ #define IS_RECOVERING(dbenv) \ (LOGGING_ON(dbenv) && \ F_ISSET((DB_LOG *)(dbenv)->lg_handle, DBLOG_RECOVER)) -/* Most initialization methods cannot be called after open is called. */ +/* Initialization methods are often illegal before/after open is called. */ #define ENV_ILLEGAL_AFTER_OPEN(dbenv, name) \ if (F_ISSET((dbenv), DB_ENV_OPEN_CALLED)) \ return (__db_mi_open(dbenv, name, 1)); +#define ENV_ILLEGAL_BEFORE_OPEN(dbenv, name) \ + if (!F_ISSET((dbenv), DB_ENV_OPEN_CALLED)) \ + return (__db_mi_open(dbenv, name, 0)); /* We're not actually user hostile, honest. */ -#define ENV_REQUIRES_CONFIG(dbenv, handle, subsystem) \ +#define ENV_REQUIRES_CONFIG(dbenv, handle, i, flags) \ if (handle == NULL) \ - return (__db_env_config(dbenv, subsystem)); + return (__db_env_config(dbenv, i, flags)); /******************************************************* * Database Access Methods. @@ -234,15 +276,15 @@ typedef enum { /* Initialization methods are often illegal before/after open is called. */ #define DB_ILLEGAL_AFTER_OPEN(dbp, name) \ - if (F_ISSET((dbp), DB_OPEN_CALLED)) \ - return (__db_mi_open(dbp->dbenv, name, 1)); + if (F_ISSET((dbp), DB_AM_OPEN_CALLED)) \ + return (__db_mi_open((dbp)->dbenv, name, 1)); #define DB_ILLEGAL_BEFORE_OPEN(dbp, name) \ - if (!F_ISSET((dbp), DB_OPEN_CALLED)) \ - return (__db_mi_open(dbp->dbenv, name, 0)); + if (!F_ISSET((dbp), DB_AM_OPEN_CALLED)) \ + return (__db_mi_open((dbp)->dbenv, name, 0)); /* Some initialization methods are illegal if environment isn't local. */ #define DB_ILLEGAL_IN_ENV(dbp, name) \ - if (!F_ISSET(dbp->dbenv, DB_ENV_DBLOCAL)) \ - return (__db_mi_env(dbp->dbenv, name)); + if (!F_ISSET((dbp)->dbenv, DB_ENV_DBLOCAL)) \ + return (__db_mi_env((dbp)->dbenv, name)); #define DB_ILLEGAL_METHOD(dbp, flags) { \ int __ret; \ if ((__ret = __dbh_am_chk(dbp, flags)) != 0) \ @@ -268,12 +310,49 @@ struct __dbc_internal { __DBC_INTERNAL }; +/* Actions that __db_master_update can take. */ +typedef enum { MU_REMOVE, MU_RENAME, MU_OPEN } mu_action; + /* * Access-method-common macro for determining whether a cursor * has been initialized. */ #define IS_INITIALIZED(dbc) ((dbc)->internal->pgno != PGNO_INVALID) +/* Free the callback-allocated buffer, if necessary, hanging off of a DBT. */ +#define FREE_IF_NEEDED(sdbp, dbt) \ + if (F_ISSET((dbt), DB_DBT_APPMALLOC)) { \ + __os_ufree((sdbp)->dbenv, (dbt)->data); \ + F_CLR((dbt), DB_DBT_APPMALLOC); \ + } + +/* + * Use memory belonging to object "owner" to return the results of + * any no-DBT-flag get ops on cursor "dbc". + */ +#define SET_RET_MEM(dbc, owner) \ + do { \ + (dbc)->rskey = &(owner)->my_rskey; \ + (dbc)->rkey = &(owner)->my_rkey; \ + (dbc)->rdata = &(owner)->my_rdata; \ + } while (0) + +/* Use the return-data memory src is currently set to use in dest as well. */ +#define COPY_RET_MEM(src, dest) \ + do { \ + (dest)->rskey = (src)->rskey; \ + (dest)->rkey = (src)->rkey; \ + (dest)->rdata = (src)->rdata; \ + } while (0) + +/* Reset the returned-memory pointers to their defaults. */ +#define RESET_RET_MEM(dbc) \ + do { \ + (dbc)->rskey = &(dbc)->my_rskey; \ + (dbc)->rkey = &(dbc)->my_rkey; \ + (dbc)->rdata = &(dbc)->my_rdata; \ + } while (0) + /******************************************************* * Mpool. *******************************************************/ @@ -286,7 +365,8 @@ struct __dbc_internal { /* Structure used as the DB pgin/pgout pgcookie. */ typedef struct __dbpginfo { size_t db_pagesize; /* Underlying page size. */ - int needswap; /* If swapping required. */ + u_int32_t flags; /* Some DB_AM flags needed. */ + DBTYPE type; /* DB type */ } DB_PGINFO; /******************************************************* @@ -297,102 +377,108 @@ typedef struct __dbpginfo { (LSN).file = 0; \ (LSN).offset = 0; \ } while (0) - -/* Return 1 if LSN is a 'zero' lsn, otherwise return 0. */ #define IS_ZERO_LSN(LSN) ((LSN).file == 0) -/* Test if we need to log a change. */ -#define DB_LOGGING(dbc) \ - (LOGGING_ON((dbc)->dbp->dbenv) && !F_ISSET(dbc, DBC_RECOVER)) +#define IS_INIT_LSN(LSN) ((LSN).file == 1 && (LSN).offset == 0) +#define INIT_LSN(LSN) do { \ + (LSN).file = 1; \ + (LSN).offset = 0; \ +} while (0) + +#define MAX_LSN(LSN) do { \ + (LSN).file = UINT32_T_MAX; \ + (LSN).offset = UINT32_T_MAX; \ +} while (0) +#define IS_MAX_LSN(LSN) \ + ((LSN).file == UINT32_T_MAX && (LSN).offset == UINT32_T_MAX) + +/* If logging is turned off, smash the lsn. */ +#define LSN_NOT_LOGGED(LSN) do { \ + (LSN).file = 0; \ + (LSN).offset = 1; \ +} while (0) +#define IS_NOT_LOGGED_LSN(LSN) \ + ((LSN).file == 0 && (LSN).offset == 1) -/* Internal flag for use with internal __log_unregister. */ -#define DB_LOGONLY 0x01 /******************************************************* * Txn. *******************************************************/ #define DB_NONBLOCK(C) ((C)->txn != NULL && F_ISSET((C)->txn, TXN_NOWAIT)) -#define IS_SUBTRANSACTION(txn) \ +#define IS_SUBTRANSACTION(txn) \ ((txn) != NULL && (txn)->parent != NULL) /******************************************************* - * Global variables. + * Crypto. *******************************************************/ -#ifdef HAVE_VXWORKS -#include "semLib.h" -#endif +#define DB_IV_BYTES 16 /* Bytes per IV */ +#define DB_MAC_KEY 20 /* Bytes per MAC checksum */ -/* - * DB global variables. Done in a single structure to minimize the name-space - * pollution. - */ -typedef struct __db_globals { - u_int32_t db_pageyield; /* db_set_pageyield */ - u_int32_t db_panic; /* db_set_panic */ - u_int32_t db_region_init; /* db_set_region_init */ - u_int32_t db_tas_spins; /* db_set_tas_spins */ -#ifdef HAVE_VXWORKS - u_int32_t db_global_init; /* VxWorks: inited */ - SEM_ID db_global_lock; /* VxWorks: global semaphore */ -#endif - /* XA: list of opened environments. */ - TAILQ_HEAD(__db_envq, __db_env) db_envq; -} DB_GLOBALS; - -#ifdef DB_INITIALIZE_DB_GLOBALS -DB_GLOBALS __db_global_values = { - 0, /* db_set_pageyield */ - 1, /* db_set_panic */ - 0, /* db_set_region_init */ - 0, /* db_set_tas_spins */ -#ifdef HAVE_VXWORKS - 0, /* db_global_init */ - NULL, /* db_global_lock */ -#endif - /* XA environment queue */ - {NULL, &__db_global_values.db_envq.tqh_first} -}; -#else -extern DB_GLOBALS __db_global_values; -#endif -#define DB_GLOBAL(v) __db_global_values.v - -/* Forward structure declarations. */ +/******************************************************* + * Forward structure declarations. + *******************************************************/ struct __db_reginfo_t; typedef struct __db_reginfo_t REGINFO; -struct __mutex_t; typedef struct __mutex_t MUTEX; +struct __db_txnhead; typedef struct __db_txnhead DB_TXNHEAD; +struct __db_txnlist; typedef struct __db_txnlist DB_TXNLIST; struct __vrfy_childinfo; typedef struct __vrfy_childinfo VRFY_CHILDINFO; struct __vrfy_dbinfo; typedef struct __vrfy_dbinfo VRFY_DBINFO; struct __vrfy_pageinfo; typedef struct __vrfy_pageinfo VRFY_PAGEINFO; -struct __db_txnlist; typedef struct __db_txnlist DB_TXNLIST; -struct __db_txnhead; typedef struct __db_txnhead DB_TXNHEAD; -typedef enum { - TXNLIST_DELETE, - TXNLIST_LSN, - TXNLIST_TXNID, - TXNLIST_PGNO -} db_txnlist_type; - -/* - * Currently, region offsets are limited to 32-bits. I expect that's going - * to have to be fixed in the not-too-distant future, since we won't want to - * split 100Gb memory pools into that many different regions. It's typedef'd - * so it won't be too painful to upgrade. - */ -typedef u_int32_t roff_t; #if defined(__cplusplus) } #endif /******************************************************* - * More general includes. + * Remaining general DB includes. + *******************************************************/ + + +#include "dbinc/globals.h" +#include "dbinc/debug.h" +#include "dbinc/mutex.h" +#include "dbinc/region.h" +#include "dbinc_auto/mutex_ext.h" /* XXX: Include after region.h. */ +#include "dbinc_auto/env_ext.h" +#include "dbinc/os.h" +#include "dbinc/rep.h" +#include "dbinc_auto/clib_ext.h" +#include "dbinc_auto/common_ext.h" + +/******************************************************* + * Remaining Log. + * These need to be defined after the general includes + * because they need rep.h from above. *******************************************************/ -#include "debug.h" -#include "mutex.h" -#include "region.h" -#include "mutex_ext.h" -#include "env_ext.h" -#include "os.h" -#include "os_ext.h" -#include "common_ext.h" +/* + * Test if the environment is currently logging changes. If we're in recovery + * or we're a replication client, we don't need to log changes because they're + * already in the log, even though we have a fully functional log system. + */ +#define DBENV_LOGGING(dbenv) \ + (LOGGING_ON(dbenv) && !IS_REP_CLIENT(dbenv) && \ + (!IS_RECOVERING(dbenv))) + +/* + * Test if we need to log a change. By default, we don't log operations without + * associated transactions, unless DIAGNOSTIC, DEBUG_ROP or DEBUG_WOP are on. + * This is because we want to get log records for read/write operations, and, if + * we trying to debug something, more information is always better. + * + * The DBC_RECOVER flag is set when we're in abort, as well as during recovery; + * thus DBC_LOGGING may be false for a particular dbc even when DBENV_LOGGING + * is true. + * + * We explicitly use LOGGING_ON/IS_REP_CLIENT here because we don't want to pull + * in the log headers, which IS_RECOVERING (and thus DBENV_LOGGING) rely on, and + * because DBC_RECOVER should be set anytime IS_RECOVERING would be true. + */ +#if defined(DIAGNOSTIC) || defined(DEBUG_ROP) || defined(DEBUG_WOP) +#define DBC_LOGGING(dbc) \ + (LOGGING_ON((dbc)->dbp->dbenv) && \ + !F_ISSET((dbc), DBC_RECOVER) && !IS_REP_CLIENT((dbc)->dbp->dbenv)) +#else +#define DBC_LOGGING(dbc) \ + ((dbc)->txn != NULL && LOGGING_ON((dbc)->dbp->dbenv) && \ + !F_ISSET((dbc), DBC_RECOVER) && !IS_REP_CLIENT((dbc)->dbp->dbenv)) +#endif #endif /* !_DB_INTERNAL_H_ */ |