summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/btree/bt_cache.c4
-rw-r--r--src/btree/bt_evict.c4
-rw-r--r--src/conn/conn_api.c31
-rw-r--r--src/conn/conn_btree.c9
-rw-r--r--src/conn/conn_handle.c4
-rw-r--r--src/conn/conn_open.c17
-rw-r--r--src/include/api.h13
-rw-r--r--src/session/session_api.c6
-rw-r--r--src/session/session_btree.c2
-rw-r--r--src/support/err.c60
10 files changed, 85 insertions, 65 deletions
diff --git a/src/btree/bt_cache.c b/src/btree/bt_cache.c
index b4256ba6f85..ce34ac63dcf 100644
--- a/src/btree/bt_cache.c
+++ b/src/btree/bt_cache.c
@@ -19,7 +19,7 @@ __wt_cache_create(WT_CONNECTION_IMPL *conn, const char *cfg[])
WT_DECL_RET;
WT_SESSION_IMPL *session;
- session = &conn->default_session;
+ session = conn->default_session;
WT_RET(__wt_calloc_def(session, 1, &conn->cache));
cache = conn->cache;
@@ -90,7 +90,7 @@ __wt_cache_destroy(WT_CONNECTION_IMPL *conn)
WT_SESSION_IMPL *session;
WT_CACHE *cache;
- session = &conn->default_session;
+ session = conn->default_session;
cache = conn->cache;
if (cache == NULL)
diff --git a/src/btree/bt_evict.c b/src/btree/bt_evict.c
index bab00b68384..1ecdc473e87 100644
--- a/src/btree/bt_evict.c
+++ b/src/btree/bt_evict.c
@@ -258,7 +258,7 @@ __wt_cache_evict_server(void *arg)
* We need a session handle because we're reading/writing pages.
* Start with the default session to keep error handling simple.
*/
- session = &conn->default_session;
+ session = conn->default_session;
WT_ERR(__wt_open_session(conn, 1, NULL, NULL, &session));
while (F_ISSET(conn, WT_SERVER_RUN)) {
@@ -296,7 +296,7 @@ err: __wt_err(session, ret, "eviction server error");
__wt_free(session, cache->evict);
- if (session != &conn->default_session)
+ if (session != conn->default_session)
(void)session->iface.close(&session->iface, NULL);
return (NULL);
diff --git a/src/conn/conn_api.c b/src/conn/conn_api.c
index 83892d31f09..b559797243c 100644
--- a/src/conn/conn_api.c
+++ b/src/conn/conn_api.c
@@ -121,7 +121,7 @@ __conn_remove_collator(WT_CONNECTION_IMPL *conn, WT_NAMED_COLLATOR *ncoll)
{
WT_SESSION_IMPL *session;
- session = &conn->default_session;
+ session = conn->default_session;
/* Remove from the connection's list. */
TAILQ_REMOVE(&conn->collqh, ncoll, q);
@@ -174,7 +174,7 @@ __conn_remove_compressor(WT_CONNECTION_IMPL *conn, WT_NAMED_COMPRESSOR *ncomp)
{
WT_SESSION_IMPL *session;
- session = &conn->default_session;
+ session = conn->default_session;
/* Remove from the connection's list. */
TAILQ_REMOVE(&conn->compqh, ncomp, q);
@@ -232,7 +232,7 @@ __conn_remove_data_source(
{
WT_SESSION_IMPL *session;
- session = &conn->default_session;
+ session = conn->default_session;
/* Remove from the connection's list. */
TAILQ_REMOVE(&conn->dsrcqh, ndsrc, q);
@@ -382,7 +382,7 @@ __conn_config(WT_CONNECTION_IMPL *conn, const char **cfg, WT_ITEM **cbufp)
cbuf = NULL;
fh = NULL;
- session = &conn->default_session;
+ session = conn->default_session;
/* Check for an optional configuration file. */
#define WT_CONFIGFILE "WiredTiger.config"
@@ -524,7 +524,7 @@ __conn_home(WT_CONNECTION_IMPL *conn, const char *home, const char **cfg)
WT_CONFIG_ITEM cval;
WT_SESSION_IMPL *session;
- session = &conn->default_session;
+ session = conn->default_session;
/* If the application specifies a home directory, use it. */
if (home != NULL)
@@ -580,7 +580,7 @@ __conn_single(WT_CONNECTION_IMPL *conn, const char **cfg)
int created;
char buf[256];
- session = &conn->default_session;
+ session = conn->default_session;
#define WT_FLAGFILE "WiredTiger"
/*
@@ -725,16 +725,11 @@ wiredtiger_open(const char *home, WT_EVENT_HANDLER *event_handler,
TAILQ_INSERT_TAIL(&__wt_process.connqh, conn, q);
__wt_spin_unlock(NULL, &__wt_process.spinlock);
- session = &conn->default_session;
+ conn->default_session = session = &conn->dummy_session;
session->iface.connection = &conn->iface;
session->name = "wiredtiger_open";
-
- /*
- * Configure any event handlers provided by the application as soon as
- * possible so errors are handled correctly.
- */
- if (event_handler != NULL)
- session->event_handler = event_handler;
+ session->event_handler = (event_handler != NULL) ?
+ event_handler : __wt_event_handler_default;
/* Remaining basic initialization of the connection structure. */
WT_ERR(__wt_connection_init(conn));
@@ -757,7 +752,7 @@ wiredtiger_open(const char *home, WT_EVENT_HANDLER *event_handler,
WT_ERR(__wt_config_gets(session, cfg, "hazard_max", &cval));
conn->hazard_size = (uint32_t)cval.val;
WT_ERR(__wt_config_gets(session, cfg, "session_max", &cval));
- conn->session_size = (uint32_t)cval.val;
+ conn->session_size = (uint32_t)cval.val + WT_NUM_INTERNAL_SESSIONS;
WT_ERR(__wt_config_gets(session, cfg, "sync", &cval));
if (!cval.val)
F_SET(conn, WT_CONN_NOSYNC);
@@ -828,16 +823,16 @@ wiredtiger_open(const char *home, WT_EVENT_HANDLER *event_handler,
WT_ERR(ret);
}
+ WT_ERR(__wt_open_session(conn, 1, NULL, NULL, &conn->default_session));
+ session = conn->default_session;
+
/*
* Check on the turtle and metadata files, creating them if necessary
* (which avoids application threads racing to create the metadata file
* later). We need a session handle for this, open one.
*/
- WT_ERR(__wt_open_session(conn, 0, NULL, NULL, &session));
if ((ret = __wt_turtle_init(session, &exist)) == 0 && !exist)
ret = __wt_schema_create(session, WT_METADATA_URI, NULL);
- WT_TRET(session->iface.close(&session->iface, NULL));
- session = &conn->default_session;
WT_ERR(ret);
STATIC_ASSERT(offsetof(WT_CONNECTION_IMPL, iface) == 0);
diff --git a/src/conn/conn_btree.c b/src/conn/conn_btree.c
index 9763329fe21..6bd9a2c94aa 100644
--- a/src/conn/conn_btree.c
+++ b/src/conn/conn_btree.c
@@ -367,11 +367,7 @@ __wt_conn_btree_discard(WT_CONNECTION_IMPL *conn)
WT_DECL_RET;
WT_SESSION_IMPL *session;
- /*
- * We need a session handle because we're potentially reading/writing
- * pages.
- */
- WT_RET(__wt_open_session(conn, 1, NULL, NULL, &session));
+ session = conn->default_session;
/*
* Close open btree handles: first, everything but the metadata file
@@ -407,8 +403,5 @@ restart:
WT_TRET(__conn_btree_discard(session, btree));
}
- /* Discard our session. */
- WT_TRET(session->iface.close(&session->iface, NULL));
-
return (ret);
}
diff --git a/src/conn/conn_handle.c b/src/conn/conn_handle.c
index 42c9ac7e871..d02ef1ec7e3 100644
--- a/src/conn/conn_handle.c
+++ b/src/conn/conn_handle.c
@@ -16,7 +16,7 @@ __wt_connection_init(WT_CONNECTION_IMPL *conn)
{
WT_SESSION_IMPL *session;
- session = &conn->default_session;
+ session = conn->default_session;
TAILQ_INIT(&conn->btqh); /* WT_BTREE list */
TAILQ_INIT(&conn->dlhqh); /* Library list */
@@ -49,7 +49,7 @@ __wt_connection_destroy(WT_CONNECTION_IMPL *conn)
{
WT_SESSION_IMPL *session;
- session = &conn->default_session;
+ session = conn->default_session;
/* Check there's something to destroy. */
if (conn == NULL)
diff --git a/src/conn/conn_open.c b/src/conn/conn_open.c
index de64ba3c818..17e1a41ccf2 100644
--- a/src/conn/conn_open.c
+++ b/src/conn/conn_open.c
@@ -18,9 +18,8 @@ __wt_connection_open(WT_CONNECTION_IMPL *conn, const char *cfg[])
WT_SESSION_IMPL *session;
/* Default session. */
- conn->default_session.iface.connection = &conn->iface;
-
- session = &conn->default_session;
+ session = conn->default_session;
+ session->iface.connection = &conn->iface;
/* WT_SESSION_IMPL and hazard arrays. */
WT_ERR(__wt_calloc(session,
@@ -64,7 +63,7 @@ __wt_connection_close(WT_CONNECTION_IMPL *conn)
WT_DLH *dlh;
WT_FH *fh;
- session = &conn->default_session;
+ session = conn->default_session;
/*
* Complain if files weren't closed (ignoring the lock and logging
@@ -96,6 +95,16 @@ __wt_connection_close(WT_CONNECTION_IMPL *conn)
WT_TRET(__wt_dlclose(session, dlh));
}
+ /*
+ * Close the default session and switch back to the dummy session in
+ * case of any error messages from the remaining operations while
+ * destroying the connection handle.
+ */
+ if (session != &conn->dummy_session) {
+ WT_TRET(session->iface.close(&session->iface, NULL));
+ conn->default_session = &conn->dummy_session;
+ }
+
/* Destroy the handle. */
__wt_connection_destroy(conn);
diff --git a/src/include/api.h b/src/include/api.h
index fba3c512e16..22b7c93df4d 100644
--- a/src/include/api.h
+++ b/src/include/api.h
@@ -141,14 +141,21 @@ struct __wt_named_data_source {
};
/*
+ * Allocate some additional slots for internal sessions. There is a default
+ * session for each connection, plus a session for the eviction thread.
+ */
+#define WT_NUM_INTERNAL_SESSIONS 2
+
+/*
* WT_CONNECTION_IMPL --
* Implementation of WT_CONNECTION
*/
struct __wt_connection_impl {
WT_CONNECTION iface;
- WT_SESSION_IMPL default_session;/* For operations without an
- application-supplied session */
+ /* For operations without an application-supplied session */
+ WT_SESSION_IMPL *default_session;
+ WT_SESSION_IMPL dummy_session;
WT_SPINLOCK fh_lock; /* File handle queue spinlock */
WT_SPINLOCK serial_lock; /* Serial function call spinlock */
@@ -272,7 +279,7 @@ struct __wt_connection_impl {
API_CALL(s, session, n, NULL, NULL, cfg, cfgvar);
#define CONNECTION_API_CALL(conn, s, n, cfg, cfgvar) \
- s = &conn->default_session; \
+ s = conn->default_session; \
API_CALL(s, connection, n, NULL, NULL, cfg, cfgvar); \
#define CURSOR_API_CALL(cur, s, n, bt) \
diff --git a/src/session/session_api.c b/src/session/session_api.c
index 3cd20c934db..2a285b25810 100644
--- a/src/session/session_api.c
+++ b/src/session/session_api.c
@@ -75,7 +75,7 @@ __session_close(WT_SESSION *wt_session, const char *config)
*/
WT_PUBLISH(session->iface.connection, NULL);
- session = &conn->default_session;
+ session = conn->default_session;
__wt_spin_unlock(session, &conn->spinlock);
err: API_END_NOTFOUND_MAP(session, ret);
@@ -152,7 +152,7 @@ __session_create(WT_SESSION *wt_session, const char *uri, const char *config)
WT_UNUSED(cfg);
/* Disallow objects in the WiredTiger name space. */
- WT_RET(__wt_schema_name_check(session, uri));
+ WT_ERR(__wt_schema_name_check(session, uri));
WT_ERR(__wt_schema_create(session, uri, config));
@@ -473,7 +473,7 @@ __wt_open_session(WT_CONNECTION_IMPL *conn, int internal,
WT_UNUSED(config);
- session = &conn->default_session;
+ session = conn->default_session;
session_ret = NULL;
__wt_spin_lock(session, &conn->spinlock);
diff --git a/src/session/session_btree.c b/src/session/session_btree.c
index 13d659fe1e1..485a06ee698 100644
--- a/src/session/session_btree.c
+++ b/src/session/session_btree.c
@@ -165,7 +165,7 @@ __wt_session_get_btree(WT_SESSION_IMPL *session,
return (ret);
}
}
-
+
/*
* Reading the metadata doubles as an existence check. If it fails, we
* can't open the file anyway, so it might as well not exist.
diff --git a/src/support/err.c b/src/support/err.c
index 9cc36b2a557..9a279ff6e5b 100644
--- a/src/support/err.c
+++ b/src/support/err.c
@@ -12,12 +12,14 @@
* Default WT_EVENT_HANDLER->handle_error implementation: send to stderr.
*/
static int
-__handle_error_default(int error, const char *errmsg)
+__handle_error_default(WT_EVENT_HANDLER *handler, int error, const char *errmsg)
{
size_t len_err, len_errmsg;
const char *err;
int cprint;
+ WT_UNUSED(handler);
+
if (error != 0) {
err = wiredtiger_strerror(error);
len_err = strlen(err);
@@ -38,16 +40,41 @@ __handle_error_default(int error, const char *errmsg)
* Default WT_EVENT_HANDLER->handle_message implementation: send to stdout.
*/
static int
-__handle_message_default(const char *message)
+__handle_message_default(WT_EVENT_HANDLER *handler, const char *message)
{
int cprint;
+ WT_UNUSED(handler);
+
cprint = printf("%s\n", message);
return (cprint >= 0 ? 0 : EIO);
}
/*
+ * __handle_progress_default --
+ * Default WT_EVENT_HANDLER->handle_progress implementation: ignore.
+ */
+static int
+__handle_progress_default(
+ WT_EVENT_HANDLER *handler, const char *operation, uint64_t progress)
+{
+ WT_UNUSED(handler);
+ WT_UNUSED(operation);
+ WT_UNUSED(progress);
+
+ return (0);
+}
+
+static WT_EVENT_HANDLER __event_handler_default = {
+ __handle_error_default,
+ __handle_message_default,
+ __handle_progress_default
+};
+
+WT_EVENT_HANDLER *__wt_event_handler_default = &__event_handler_default;
+
+/*
* __handler_failure --
* Report the failure of an application-configured event handler.
*/
@@ -71,15 +98,15 @@ __handler_failure(WT_SESSION_IMPL *session,
/*
* Use the error handler to report the failure, unless it was the error
* handler that failed. If it was the error handler that failed, or a
- * called to the error handler fails, use the default error handler.
+ * call to the error handler fails, use the default error handler.
*/
handler = session->event_handler;
if (!error_handler_failed &&
- handler != NULL && handler->handle_error != NULL &&
- handler->handle_error(handler, error, s) == 0)
+ handler->handle_error != __handle_error_default &&
+ handler->handle_error(handler, error, s) == 0)
return;
- (void)__handle_error_default(error, s);
+ (void)__handle_error_default(NULL, error, s);
}
/*
@@ -140,20 +167,13 @@ __eventv(WT_SESSION_IMPL *session, int msg_event, int error,
*/
handler = session->event_handler;
if (msg_event) {
- if (handler == NULL || handler->handle_message == NULL)
- ret = __handle_message_default(s);
- else
- ret = handler->handle_message(handler, s);
+ ret = handler->handle_message(handler, s);
if (ret != 0)
__handler_failure(session, ret, "message", 0);
} else {
- if (handler == NULL || handler->handle_error == NULL)
- ret = __handle_error_default(error, s);
- else {
- ret = handler->handle_error(handler, error, s);
- if (ret != 0)
- __handler_failure(session, ret, "error", 1);
- }
+ ret = handler->handle_error(handler, error, s);
+ if (ret != 0 && handler->handle_error != __handle_error_default)
+ __handler_failure(session, ret, "error", 1);
}
return (ret);
@@ -243,11 +263,7 @@ __wt_vmsg(WT_SESSION_IMPL *session, const char *fmt, va_list ap)
(void)vsnprintf(s, sizeof(s), fmt, ap);
handler = session->event_handler;
- if (handler == NULL || handler->handle_message == NULL)
- return (__handle_message_default(s));
- else
- return (handler->handle_message(handler, s));
- /* NOTREACHED */
+ return (handler->handle_message(handler, s));
}
/*