summaryrefslogtreecommitdiff
path: root/db/env/env_stat.c
diff options
context:
space:
mode:
Diffstat (limited to 'db/env/env_stat.c')
-rw-r--r--db/env/env_stat.c341
1 files changed, 156 insertions, 185 deletions
diff --git a/db/env/env_stat.c b/db/env/env_stat.c
index c9ab7a112..241a1c5cd 100644
--- a/db/env/env_stat.c
+++ b/db/env/env_stat.c
@@ -1,21 +1,16 @@
/*-
* See the file LICENSE for redistribution information.
*
- * Copyright (c) 1996-2004
- * Sleepycat Software. All rights reserved.
+ * Copyright (c) 1996-2006
+ * Oracle Corporation. All rights reserved.
*
- * $Id: env_stat.c,v 1.21 2004/10/29 17:37:23 bostic Exp $
+ * $Id: env_stat.c,v 12.36 2006/09/08 19:25:15 bostic Exp $
*/
#include "db_config.h"
-#ifndef NO_SYSTEM_INCLUDES
-#include <sys/types.h>
-#endif
-
#include "db_int.h"
#include "dbinc/db_page.h"
-#include "dbinc/db_shash.h"
#include "dbinc/db_am.h"
#include "dbinc/lock.h"
#include "dbinc/log.h"
@@ -23,23 +18,27 @@
#include "dbinc/txn.h"
#ifdef HAVE_STATISTICS
-static int __dbenv_print_all __P((DB_ENV *, u_int32_t));
-static int __dbenv_print_stats __P((DB_ENV *, u_int32_t));
-static int __dbenv_stat_print __P((DB_ENV *, u_int32_t));
-static const char *__reg_type __P((reg_type_t));
+static int __env_print_all __P((DB_ENV *, u_int32_t));
+static int __env_print_stats __P((DB_ENV *, u_int32_t));
+static int __env_print_threads __P((DB_ENV *));
+static int __env_stat_print __P((DB_ENV *, u_int32_t));
+static char *__env_thread_state_print __P((DB_THREAD_STATE));
+static const char *
+ __reg_type __P((reg_type_t));
/*
- * __dbenv_stat_print_pp --
+ * __env_stat_print_pp --
* DB_ENV->stat_print pre/post processor.
*
- * PUBLIC: int __dbenv_stat_print_pp __P((DB_ENV *, u_int32_t));
+ * PUBLIC: int __env_stat_print_pp __P((DB_ENV *, u_int32_t));
*/
int
-__dbenv_stat_print_pp(dbenv, flags)
+__env_stat_print_pp(dbenv, flags)
DB_ENV *dbenv;
u_int32_t flags;
{
- int rep_check, ret;
+ DB_THREAD_INFO *ip;
+ int ret;
PANIC_CHECK(dbenv);
ENV_ILLEGAL_BEFORE_OPEN(dbenv, "DB_ENV->stat_print");
@@ -48,32 +47,36 @@ __dbenv_stat_print_pp(dbenv, flags)
flags, DB_STAT_ALL | DB_STAT_CLEAR | DB_STAT_SUBSYSTEM)) != 0)
return (ret);
- rep_check = IS_ENV_REPLICATED(dbenv) ? 1 : 0;
- if (rep_check)
- __env_rep_enter(dbenv);
- ret = __dbenv_stat_print(dbenv, flags);
- if (rep_check)
- __env_db_rep_exit(dbenv);
+ ENV_ENTER(dbenv, ip);
+ REPLICATION_WRAP(dbenv, (__env_stat_print(dbenv, flags)), ret);
+ ENV_LEAVE(dbenv, ip);
return (ret);
}
/*
- * __dbenv_stat_print --
+ * __env_stat_print --
* DB_ENV->stat_print method.
*/
static int
-__dbenv_stat_print(dbenv, flags)
+__env_stat_print(dbenv, flags)
DB_ENV *dbenv;
u_int32_t flags;
{
- DB *dbp;
+ time_t now;
int ret;
+ char time_buf[CTIME_BUFLEN];
+
+ (void)time(&now);
+ __db_msg(dbenv, "%.24s\tLocal time", __db_ctime(&now, time_buf));
- if ((ret = __dbenv_print_stats(dbenv, flags)) != 0)
+ if ((ret = __env_print_stats(dbenv, flags)) != 0)
return (ret);
if (LF_ISSET(DB_STAT_ALL) &&
- (ret = __dbenv_print_all(dbenv, flags)) != 0)
+ (ret = __env_print_all(dbenv, flags)) != 0)
+ return (ret);
+
+ if ((ret = __env_print_threads(dbenv)) != 0)
return (ret);
if (!LF_ISSET(DB_STAT_SUBSYSTEM))
@@ -86,6 +89,10 @@ __dbenv_stat_print(dbenv, flags)
__db_msg(dbenv, "%s", DB_GLOBAL(db_line));
if ((ret = __log_stat_print(dbenv, flags)) != 0)
return (ret);
+
+ __db_msg(dbenv, "%s", DB_GLOBAL(db_line));
+ if ((ret = __dbreg_stat_print(dbenv, flags)) != 0)
+ return (ret);
}
if (LOCKING_ON(dbenv)) {
@@ -112,33 +119,28 @@ __dbenv_stat_print(dbenv, flags)
return (ret);
}
- MUTEX_THREAD_LOCK(dbenv, dbenv->dblist_mutexp);
- for (dbp = LIST_FIRST(&dbenv->dblist);
- dbp != NULL; dbp = LIST_NEXT(dbp, dblistlinks)) {
+ if (MUTEX_ON(dbenv)) {
__db_msg(dbenv, "%s", DB_GLOBAL(db_line));
- __db_msg(dbenv, "%s%s%s\tDatabase name",
- dbp->fname, dbp->dname == NULL ? "" : "/",
- dbp->dname == NULL ? "" : dbp->dname);
- if ((ret = __db_stat_print(dbp, flags)) != 0)
- break;
+ if ((ret = __mutex_stat_print(dbenv, flags)) != 0)
+ return (ret);
}
- MUTEX_THREAD_UNLOCK(dbenv, dbenv->dblist_mutexp);
- return (ret);
+ return (0);
}
/*
- * __dbenv_print_stats --
+ * __env_print_stats --
* Display the default environment statistics.
*
*/
static int
-__dbenv_print_stats(dbenv, flags)
+__env_print_stats(dbenv, flags)
DB_ENV *dbenv;
u_int32_t flags;
{
REGENV *renv;
REGINFO *infop;
+ char time_buf[CTIME_BUFLEN];
infop = dbenv->reginfo;
renv = infop->primary;
@@ -147,24 +149,27 @@ __dbenv_print_stats(dbenv, flags)
__db_msg(dbenv, "%s", DB_GLOBAL(db_line));
__db_msg(dbenv, "Default database environment information:");
}
- __db_msg(dbenv, "%d.%d.%d\tEnvironment version",
- renv->majver, renv->minver, renv->patch);
STAT_HEX("Magic number", renv->magic);
- STAT_LONG("Panic value", renv->envpanic);
+ STAT_LONG("Panic value", renv->panic);
+ __db_msg(dbenv, "%d.%d.%d\tEnvironment version",
+ renv->majver, renv->minver, renv->patchver);
+ __db_msg(dbenv,
+ "%.24s\tCreation time", __db_ctime(&renv->timestamp, time_buf));
+ STAT_HEX("Environment ID", renv->envid);
+ __mutex_print_debug_single(dbenv,
+ "Primary region allocation and reference count mutex",
+ renv->mtx_regenv, flags);
STAT_LONG("References", renv->refcnt);
- __db_print_mutex(dbenv, NULL, &renv->mutex,
- "The number of region locks that required waiting", flags);
-
return (0);
}
/*
- * __dbenv_print_all --
+ * __env_print_all --
* Display the debugging environment statistics.
*/
static int
-__dbenv_print_all(dbenv, flags)
+__env_print_all(dbenv, flags)
DB_ENV *dbenv;
u_int32_t flags;
{
@@ -176,6 +181,7 @@ __dbenv_print_all(dbenv, flags)
{ DB_ENV_DBLOCAL, "DB_ENV_DBLOCAL" },
{ DB_ENV_DIRECT_DB, "DB_ENV_DIRECT_DB" },
{ DB_ENV_DIRECT_LOG, "DB_ENV_DIRECT_LOG" },
+ { DB_ENV_DSYNC_DB, "DB_ENV_DSYNC_DB" },
{ DB_ENV_DSYNC_LOG, "DB_ENV_DSYNC_LOG" },
{ DB_ENV_FATAL, "DB_ENV_FATAL" },
{ DB_ENV_LOCKDOWN, "DB_ENV_LOCKDOWN" },
@@ -200,15 +206,13 @@ __dbenv_print_all(dbenv, flags)
};
static const FN ofn[] = {
{ DB_CREATE, "DB_CREATE" },
- { DB_CXX_NO_EXCEPTIONS, "DB_CXX_NO_EXCEPTIONS" },
{ DB_FORCE, "DB_FORCE" },
{ DB_INIT_CDB, "DB_INIT_CDB" },
- { DB_INIT_LOCK, "DB_INIT_LOCK" },
+ { DB_INIT_LOCK, "DB_INIT_LOCK" },
{ DB_INIT_LOG, "DB_INIT_LOG" },
{ DB_INIT_MPOOL, "DB_INIT_MPOOL" },
{ DB_INIT_REP, "DB_INIT_REP" },
{ DB_INIT_TXN, "DB_INIT_TXN" },
- { DB_JOINENV, "DB_JOINENV" },
{ DB_LOCKDOWN, "DB_LOCKDOWN" },
{ DB_NOMMAP, "DB_NOMMAP" },
{ DB_PRIVATE, "DB_PRIVATE" },
@@ -226,51 +230,50 @@ __dbenv_print_all(dbenv, flags)
static const FN vfn[] = {
{ DB_VERB_DEADLOCK, "DB_VERB_DEADLOCK" },
{ DB_VERB_RECOVERY, "DB_VERB_RECOVERY" },
+ { DB_VERB_REGISTER, "DB_VERB_REGISTER" },
{ DB_VERB_REPLICATION, "DB_VERB_REPLICATION" },
{ DB_VERB_WAITSFOR, "DB_VERB_WAITSFOR" },
{ 0, NULL }
};
+ static const FN regenvfn[] = {
+ { DB_REGENV_REPLOCKED, "DB_REGENV_REPLOCKED" },
+ { 0, NULL }
+ };
DB_MSGBUF mb;
REGENV *renv;
REGINFO *infop;
- REGION *rp, regs[1024];
- size_t n;
- char **p;
+ REGION *rp;
+ u_int32_t i;
+ char **p, time_buf[CTIME_BUFLEN];
infop = dbenv->reginfo;
renv = infop->primary;
DB_MSGBUF_INIT(&mb);
- /*
- * Lock the database environment while we get copies of the region
- * information.
- */
- MUTEX_LOCK(dbenv, &infop->rp->mutex);
-
- for (n = 0, rp = SH_LIST_FIRST(&renv->regionq, __db_region);
- n < sizeof(regs) / sizeof(regs[0]) && rp != NULL;
- ++n, rp = SH_LIST_NEXT(rp, q, __db_region)) {
- regs[n] = *rp;
- if (LF_ISSET(DB_STAT_CLEAR))
- MUTEX_CLEAR(&rp->mutex);
- }
- if (n > 0)
- --n;
- MUTEX_UNLOCK(dbenv, &infop->rp->mutex);
+ __db_msg(dbenv, "%s", DB_GLOBAL(db_line));
+ __db_prflags(dbenv,
+ NULL, renv->init_flags, ofn, NULL, "\tInitialization flags");
+ STAT_ULONG("Region slots", renv->region_cnt);
+ __db_prflags(dbenv,
+ NULL, renv->flags, regenvfn, NULL, "\tReplication flags");
+ __db_msg(dbenv, "%.24s\tOperation timestamp",
+ renv->op_timestamp == 0 ?
+ "!Set" : __db_ctime(&renv->op_timestamp, time_buf));
+ __db_msg(dbenv, "%.24s\tReplication timestamp",
+ renv->rep_timestamp == 0 ?
+ "!Set" : __db_ctime(&renv->rep_timestamp, time_buf));
- if (LF_ISSET(DB_STAT_ALL)) {
- __db_msg(dbenv, "%s", DB_GLOBAL(db_line));
- __db_msg(dbenv, "Per region database environment information:");
- }
- while (n > 0) {
- rp = &regs[--n];
+ __db_msg(dbenv, "%s", DB_GLOBAL(db_line));
+ __db_msg(dbenv, "Per region database environment information:");
+ for (rp = R_ADDR(infop, renv->region_off),
+ i = 0; i < renv->region_cnt; ++i, ++rp) {
+ if (rp->id == INVALID_REGION_ID)
+ continue;
__db_msg(dbenv, "%s Region:", __reg_type(rp->type));
STAT_LONG("Region ID", rp->id);
STAT_LONG("Segment ID", rp->segid);
__db_dlbytes(dbenv,
"Size", (u_long)0, (u_long)0, (u_long)rp->size);
- __db_print_mutex(dbenv, NULL, &rp->mutex,
- "The number of region locks that required waiting", flags);
}
__db_msg(dbenv, "%s", DB_GLOBAL(db_line));
@@ -278,6 +281,7 @@ __dbenv_print_all(dbenv, flags)
STAT_ISSET("Errfile", dbenv->db_errfile);
STAT_STRING("Errpfx", dbenv->db_errpfx);
STAT_ISSET("Errcall", dbenv->db_errcall);
+ STAT_ISSET("Event", dbenv->db_event_func);
STAT_ISSET("Feedback", dbenv->db_feedback);
STAT_ISSET("Panic", dbenv->db_paniccall);
STAT_ISSET("Malloc", dbenv->db_malloc);
@@ -300,36 +304,80 @@ __dbenv_print_all(dbenv, flags)
STAT_FMT("Mode", "%#o", int, dbenv->db_mode);
__db_prflags(dbenv, NULL, dbenv->open_flags, ofn, NULL, "\tOpen flags");
STAT_ISSET("Lockfhp", dbenv->lockfhp);
- STAT_ISSET("Rec tab", dbenv->recover_dtab);
- STAT_ULONG("Rec tab slots", dbenv->recover_dtab_size);
+ STAT_ISSET("Recovery table", dbenv->recover_dtab);
+ STAT_ULONG("Number of recovery table slots", dbenv->recover_dtab_size);
STAT_ISSET("RPC client", dbenv->cl_handle);
STAT_LONG("RPC client ID", dbenv->cl_id);
- STAT_LONG("DB ref count", dbenv->db_ref);
- STAT_LONG("Shared mem key", dbenv->shm_key);
- STAT_ULONG("test-and-set spin configuration", dbenv->tas_spins);
- __db_print_mutex(
- dbenv, NULL, dbenv->dblist_mutexp, "DB handle mutex", flags);
+ STAT_LONG("DB reference count", dbenv->db_ref);
+ STAT_LONG("Shared memory key", dbenv->shm_key);
+ __mutex_print_debug_single(
+ dbenv, "DB handle mutex", dbenv->mtx_dblist, flags);
STAT_ISSET("api1 internal", dbenv->api1_internal);
STAT_ISSET("api2 internal", dbenv->api2_internal);
STAT_ISSET("password", dbenv->passwd);
STAT_ISSET("crypto handle", dbenv->crypto_handle);
- __db_print_mutex(dbenv, NULL, dbenv->mt_mutexp, "MT mutex", flags);
+ __mutex_print_debug_single(dbenv, "MT mutex", dbenv->mtx_mt, flags);
__db_prflags(dbenv, NULL, dbenv->flags, fn, NULL, "\tFlags");
return (0);
}
+static char *
+__env_thread_state_print(state)
+ DB_THREAD_STATE state;
+{
+ switch (state) {
+ case THREAD_ACTIVE:
+ return ("active");
+ case THREAD_BLOCKED:
+ return ("blocked");
+ case THREAD_OUT:
+ return ("out");
+ default:
+ return ("unknown");
+ }
+}
+
+/*
+ * __env_print_threads --
+ * Display the current active threads
+ *
+ */
+static int
+__env_print_threads(dbenv)
+ DB_ENV *dbenv;
+{
+ DB_HASHTAB *htab;
+ DB_THREAD_INFO *ip;
+ u_int32_t i;
+ char buf[DB_THREADID_STRLEN];
+
+ htab = (DB_HASHTAB *)dbenv->thr_hashtab;
+ __db_msg(dbenv, "Thread status blocks:");
+ for (i = 0; i < dbenv->thr_nbucket; i++)
+ SH_TAILQ_FOREACH(ip, &htab[i], dbth_links, __db_thread_info) {
+ if (ip->dbth_state == THREAD_SLOT_NOT_IN_USE)
+ continue;
+ __db_msg(dbenv, "\tprocess/thread %s: %s",
+ dbenv->thread_id_string(
+ dbenv, ip->dbth_pid, ip->dbth_tid, buf),
+ __env_thread_state_print(ip->dbth_state));
+ }
+ return (0);
+}
+
/*
* __db_print_fh --
* Print out a file handle.
*
- * PUBLIC: void __db_print_fh __P((DB_ENV *, DB_FH *, u_int32_t));
+ * PUBLIC: void __db_print_fh __P((DB_ENV *, const char *, DB_FH *, u_int32_t));
*/
void
-__db_print_fh(dbenv, fh, flags)
+__db_print_fh(dbenv, tag, fh, flags)
DB_ENV *dbenv;
+ const char *tag;
DB_FH *fh;
u_int32_t flags;
{
@@ -340,7 +388,13 @@ __db_print_fh(dbenv, fh, flags)
{ 0, NULL }
};
- __db_print_mutex(dbenv, NULL, fh->mutexp, "file-handle.mutex", flags);
+ if (fh == NULL) {
+ STAT_ISSET(tag, fh);
+ return;
+ }
+
+ __mutex_print_debug_single(
+ dbenv, "file-handle.mutex", fh->mtx_fh, flags);
STAT_LONG("file-handle.reference count", fh->ref);
STAT_LONG("file-handle.file descriptor", fh->fd);
@@ -368,6 +422,11 @@ __db_print_fileid(dbenv, id, suffix)
DB_MSGBUF mb;
int i;
+ if (id == NULL) {
+ STAT_ISSET("ID", id);
+ return;
+ }
+
DB_MSGBUF_INIT(&mb);
for (i = 0; i < DB_FILE_ID_LEN; ++i, ++id) {
__db_msgadd(dbenv, &mb, "%x", (u_int)*id);
@@ -380,95 +439,6 @@ __db_print_fileid(dbenv, id, suffix)
}
/*
- * __db_print_mutex --
- * Print out mutex statistics.
- *
- * PUBLIC: void __db_print_mutex
- * PUBLIC: __P((DB_ENV *, DB_MSGBUF *, DB_MUTEX *, const char *, u_int32_t));
- */
-void
-__db_print_mutex(dbenv, mbp, mutex, suffix, flags)
- DB_ENV *dbenv;
- DB_MSGBUF *mbp;
- DB_MUTEX *mutex;
- const char *suffix;
- u_int32_t flags;
-{
- DB_MSGBUF mb;
- u_long value;
- int standalone;
-
- /* If we don't have a mutex, point that out and return. */
- if (mutex == NULL) {
- STAT_ISSET(suffix, mutex);
- return;
- }
-
- if (mbp == NULL) {
- DB_MSGBUF_INIT(&mb);
- mbp = &mb;
- standalone = 1;
- } else
- standalone = 0;
-
- /*
- * !!!
- * We may not hold the mutex lock -- that's OK, we're only reading
- * the statistics.
- */
- if ((value = mutex->mutex_set_wait) < 10000000)
- __db_msgadd(dbenv, mbp, "%lu", value);
- else
- __db_msgadd(dbenv, mbp, "%luM", value / 1000000);
-
- /*
- * If standalone, append the mutex percent and the locker information
- * after the suffix line. Otherwise, append it after the counter.
- *
- * The setting of "suffix" tracks "standalone" -- if standalone, expect
- * a suffix and prefix it with a <tab>, otherwise, it's optional. This
- * isn't a design, it's just the semantics we happen to need right now.
- */
- if (standalone) {
- if (suffix == NULL) /* Defense. */
- suffix = "";
-
- __db_msgadd(dbenv, &mb, "\t%s (%d%%", suffix,
- DB_PCT(mutex->mutex_set_wait,
- mutex->mutex_set_wait + mutex->mutex_set_nowait));
-#ifdef DIAGNOSTIC
-#ifdef HAVE_MUTEX_THREADS
- if (mutex->locked != 0)
- __db_msgadd(dbenv, &mb, "/%lu", (u_long)mutex->locked);
-#else
- if (mutex->pid != 0)
- __db_msgadd(dbenv, &mb, "/%lu", (u_long)mutex->pid);
-#endif
-#endif
- __db_msgadd(dbenv, &mb, ")");
-
- DB_MSGBUF_FLUSH(dbenv, mbp);
- } else {
- __db_msgadd(dbenv, mbp, "/%d%%", DB_PCT(mutex->mutex_set_wait,
- mutex->mutex_set_wait + mutex->mutex_set_nowait));
-#ifdef DIAGNOSTIC
-#ifdef HAVE_MUTEX_THREADS
- if (mutex->locked != 0)
- __db_msgadd(dbenv, &mb, "/%lu", (u_long)mutex->locked);
-#else
- if (mutex->pid != 0)
- __db_msgadd(dbenv, &mb, "/%lu", (u_long)mutex->pid);
-#endif
-#endif
- if (suffix != NULL)
- __db_msgadd(dbenv, mbp, "%s", suffix);
- }
-
- if (LF_ISSET(DB_STAT_CLEAR))
- MUTEX_CLEAR(mutex);
-}
-
-/*
* __db_dl --
* Display a big value.
*
@@ -510,12 +480,13 @@ __db_dl_pct(dbenv, msg, value, pct, tag)
/*
* Two formats: if less than 10 million, display as the number, if
- * greater than 10 million display as ###M.
+ * greater than 10 million, round it off and display as ###M.
*/
if (value < 10000000)
__db_msgadd(dbenv, &mb, "%lu\t%s", value, msg);
else
- __db_msgadd(dbenv, &mb, "%luM\t%s", value / 1000000, msg);
+ __db_msgadd(dbenv,
+ &mb, "%luM\t%s", (value + 500000) / 1000000, msg);
if (tag == NULL)
__db_msgadd(dbenv, &mb, " (%d%%)", pct);
else
@@ -602,11 +573,11 @@ __db_print_reginfo(dbenv, infop, s)
STAT_STRING("Region type", __reg_type(infop->type));
STAT_ULONG("Region ID", infop->id);
STAT_STRING("Region name", infop->name);
- STAT_HEX("Original region address", infop->addr_orig);
- STAT_HEX("Region address", infop->addr);
- STAT_HEX("Region primary address", infop->primary);
+ STAT_POINTER("Original region address", infop->addr_orig);
+ STAT_POINTER("Region address", infop->addr);
+ STAT_POINTER("Region primary address", infop->primary);
STAT_ULONG("Region maximum allocation", infop->max_alloc);
- STAT_ULONG("Region allocated", infop->max_alloc);
+ STAT_ULONG("Region allocated", infop->allocated);
__db_prflags(dbenv, NULL, infop->flags, fn, NULL, "\tRegion flags");
}
@@ -650,12 +621,12 @@ int
__db_stat_not_built(dbenv)
DB_ENV *dbenv;
{
- __db_err(dbenv, "Library build did not include statistics support");
+ __db_errx(dbenv, "Library build did not include statistics support");
return (DB_OPNOTSUP);
}
int
-__dbenv_stat_print_pp(dbenv, flags)
+__env_stat_print_pp(dbenv, flags)
DB_ENV *dbenv;
u_int32_t flags;
{