summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichael Cahill <michael.cahill@wiredtiger.com>2012-03-11 10:46:05 +1100
committerMichael Cahill <michael.cahill@wiredtiger.com>2012-03-11 10:46:05 +1100
commit405f6a3969536ae378a343b3387a433236e85d37 (patch)
tree26fa42ce7bd0aa59000addcd047acf0fe28d1ad6
parenta3de55629620c7dd9e51971f3f4201bd60acad8a (diff)
downloadmongo-405f6a3969536ae378a343b3387a433236e85d37.tar.gz
Layer dump cursors on top of any cursor type.
--HG-- extra : rebase_source : a0ddaa6ba4d7ed5fdb7ca8811f2147e3ede0bad3
-rw-r--r--src/cursor/cur_config.c3
-rw-r--r--src/cursor/cur_dump.c187
-rw-r--r--src/cursor/cur_file.c3
-rw-r--r--src/cursor/cur_index.c4
-rw-r--r--src/cursor/cur_stat.c4
-rw-r--r--src/cursor/cur_std.c14
-rw-r--r--src/cursor/cur_table.c5
-rw-r--r--src/include/cursor.h6
-rw-r--r--src/include/extern.h33
-rw-r--r--src/include/wt_internal.in2
-rw-r--r--src/session/session_root.c18
-rw-r--r--src/support/hex.c74
-rw-r--r--src/support/scratch.c14
13 files changed, 232 insertions, 135 deletions
diff --git a/src/cursor/cur_config.c b/src/cursor/cur_config.c
index e89376adcb3..1563af56417 100644
--- a/src/cursor/cur_config.c
+++ b/src/cursor/cur_config.c
@@ -67,8 +67,7 @@ __wt_curconfig_open(WT_SESSION_IMPL *session,
cursor->key_format = cursor->value_format = "S";
STATIC_ASSERT(offsetof(WT_CURSOR_CONFIG, iface) == 0);
- WT_ERR(__wt_cursor_init(cursor, uri, 0, cfg));
- *cursorp = cursor;
+ WT_ERR(__wt_cursor_init(cursor, uri, 0, cfg, cursorp));
if (0) {
err: __wt_free(session, cconfig);
diff --git a/src/cursor/cur_dump.c b/src/cursor/cur_dump.c
index 79bbbd10d63..d84a4fdf0b9 100644
--- a/src/cursor/cur_dump.c
+++ b/src/cursor/cur_dump.c
@@ -9,63 +9,36 @@
/*
* __raw_to_dump --
- * We have a buffer where the data item contains a raw value, convert it
- * to a printable string.
+ * We have a buffer where the data item contains a raw value,
+ * convert it to a printable string.
*/
static int
__raw_to_dump(
WT_SESSION_IMPL *session, WT_ITEM *from, WT_ITEM *to, int hexonly)
{
- WT_ITEM *tmp;
- uint32_t size;
-
- /*
- * In the worst case, every character takes up 3 spaces, plus a
- * trailing nul byte.
- */
- WT_RET(__wt_scr_alloc(session, from->size * 3 + 10, &tmp));
- size = from->size;
if (hexonly)
- __wt_raw_to_hex(from->data, tmp->mem, &size);
+ WT_RET(__wt_raw_to_hex(session, from->data, from->size, to));
else
- __wt_raw_to_esc_hex(from->data, tmp->mem, &size);
- tmp->size = size;
-
- __wt_buf_swap(to, tmp);
- __wt_scr_free(&tmp);
+ WT_RET(
+ __wt_raw_to_esc_hex(session, from->data, from->size, to));
return (0);
}
/*
* __dump_to_raw --
- * We have a scratch buffer where the data item contains a dump string,
+ * We have a buffer containing a dump string,
* convert it to a raw value.
*/
static int
__dump_to_raw(
WT_SESSION_IMPL *session, const char *src_arg, WT_ITEM *item, int hexonly)
{
- uint32_t size;
-
- /*
- * XXX
- * Overwrite the string in place: the underlying cursor set_key and
- * set_value functions are going to use the cursor's key and value
- * buffers, which means we can't. This should probably be fixed by
- * layering the dump cursor on top of other cursors and then we can
- * use the dump cursor's key/value buffers.
- */
if (hexonly)
- WT_RET(__wt_hex_to_raw(
- session, (void *)src_arg, (void *)src_arg, &size));
+ WT_RET(__wt_hex_to_raw(session, src_arg, item));
else
- WT_RET(__wt_esc_hex_to_raw(
- session, (void *)src_arg, (void *)src_arg, &size));
+ WT_RET(__wt_esc_hex_to_raw(session, src_arg, item));
- memset(item, 0, sizeof(WT_ITEM));
- item->data = src_arg;
- item->size = size;
return (0);
}
@@ -76,20 +49,24 @@ __dump_to_raw(
static int
__curdump_get_key(WT_CURSOR *cursor, ...)
{
+ WT_CURSOR *child;
+ WT_CURSOR_DUMP *cdump;
WT_ITEM item, *itemp;
WT_SESSION_IMPL *session;
int ret;
uint64_t recno;
va_list ap;
+ cdump = (WT_CURSOR_DUMP *)cursor;
+ child = cdump->child;
CURSOR_API_CALL(cursor, session, get_key, NULL);
if (WT_CURSOR_RECNO(cursor) && !F_ISSET(cursor, WT_CURSTD_RAW)) {
- WT_ERR(cursor->get_key(cursor, &recno));
+ WT_ERR(child->get_key(child, &recno));
WT_ERR(__wt_buf_fmt(session, &cursor->key, "%" PRIu64, recno));
} else {
- WT_ERR(cursor->get_key(cursor, &item));
+ WT_ERR(child->get_key(child, &item));
WT_ERR(__raw_to_dump(session, &item,
&cursor->key, F_ISSET(cursor, WT_CURSTD_DUMP_HEX) ? 1 : 0));
@@ -144,13 +121,16 @@ format: WT_RET_MSG(session, EINVAL, "%s: invalid record number", p);
static void
__curdump_set_key(WT_CURSOR *cursor, ...)
{
- WT_ITEM item;
+ WT_CURSOR_DUMP *cdump;
+ WT_CURSOR *child;
WT_SESSION_IMPL *session;
uint64_t recno;
va_list ap;
const char *p;
int ret;
+ cdump = (WT_CURSOR_DUMP *)cursor;
+ child = cdump->child;
CURSOR_API_CALL(cursor, session, set_key, NULL);
va_start(ap, cursor);
@@ -163,12 +143,12 @@ __curdump_set_key(WT_CURSOR *cursor, ...)
if (WT_CURSOR_RECNO(cursor) && !F_ISSET(cursor, WT_CURSTD_RAW)) {
WT_ERR(str2recno(session, p, &recno));
- cursor->set_key(cursor, recno);
+ child->set_key(child, recno);
} else {
- WT_ERR(__dump_to_raw(session,
- p, &item, F_ISSET(cursor, WT_CURSTD_DUMP_HEX) ? 1 : 0));
+ WT_ERR(__dump_to_raw(session, p, &cursor->key,
+ F_ISSET(cursor, WT_CURSTD_DUMP_HEX) ? 1 : 0));
- cursor->set_key(cursor, &item);
+ child->set_key(child, &cursor->key);
}
if (0) {
@@ -186,14 +166,18 @@ err: cursor->saved_err = ret;
static int
__curdump_get_value(WT_CURSOR *cursor, ...)
{
+ WT_CURSOR_DUMP *cdump;
+ WT_CURSOR *child;
WT_ITEM item, *itemp;
WT_SESSION_IMPL *session;
va_list ap;
int ret;
+ cdump = (WT_CURSOR_DUMP *)cursor;
+ child = cdump->child;
CURSOR_API_CALL(cursor, session, get_value, NULL);
- WT_ERR(cursor->get_value(cursor, &item));
+ WT_ERR(child->get_value(child, &item));
WT_ERR(__raw_to_dump(session, &item,
&cursor->value, F_ISSET(cursor, WT_CURSTD_DUMP_HEX) ? 1 : 0));
@@ -218,12 +202,15 @@ err: API_END(session);
static void
__curdump_set_value(WT_CURSOR *cursor, ...)
{
- WT_ITEM item;
+ WT_CURSOR_DUMP *cdump;
+ WT_CURSOR *child;
WT_SESSION_IMPL *session;
va_list ap;
int ret;
const char *p;
+ cdump = (WT_CURSOR_DUMP *)cursor;
+ child = cdump->child;
CURSOR_API_CALL(cursor, session, set_value, NULL);
va_start(ap, cursor);
@@ -234,9 +221,9 @@ __curdump_set_value(WT_CURSOR *cursor, ...)
va_end(ap);
WT_ERR(__dump_to_raw(session,
- p, &item, F_ISSET(cursor, WT_CURSTD_DUMP_HEX) ? 1 : 0));
+ p, &cursor->value, F_ISSET(cursor, WT_CURSTD_DUMP_HEX) ? 1 : 0));
- cursor->set_value(cursor, &item);
+ child->set_value(child, &cursor->value);
if (0) {
err: cursor->saved_err = ret;
@@ -246,15 +233,111 @@ err: cursor->saved_err = ret;
API_END(session);
}
+/* Pass through a call to the underlying cursor. */
+#define CURDUMP_PASS(op) \
+static int \
+__curdump_##op(WT_CURSOR *cursor) \
+{ \
+ WT_CURSOR_DUMP *cdump; \
+ \
+ cdump = (WT_CURSOR_DUMP *)cursor; \
+ return (cdump->child->op(cdump->child)); \
+}
+
+CURDUMP_PASS(next)
+CURDUMP_PASS(prev)
+CURDUMP_PASS(reset)
+CURDUMP_PASS(search)
+
+static int
+__curdump_search_near(WT_CURSOR *cursor, int *exact)
+{
+ WT_CURSOR_DUMP *cdump;
+
+ cdump = (WT_CURSOR_DUMP *)cursor;
+ return (cdump->child->search_near(cdump->child, exact));
+}
+
+CURDUMP_PASS(insert)
+CURDUMP_PASS(update)
+CURDUMP_PASS(remove)
+
+static int
+__curdump_close(WT_CURSOR *cursor)
+{
+ WT_CURSOR_DUMP *cdump;
+ WT_CURSOR *child;
+ WT_SESSION_IMPL *session;
+ int ret;
+
+ cdump = (WT_CURSOR_DUMP *)cursor;
+ child = cdump->child;
+ ret = 0;
+
+ CURSOR_API_CALL(cursor, session, get_key, NULL);
+ if (child != NULL)
+ WT_TRET(child->close(child));
+ /* We shared the child's URI. */
+ cursor->uri = NULL;
+ WT_TRET(__wt_cursor_close(cursor));
+ API_END(session);
+
+ return (ret);
+}
+
/*
* __wt_curdump_init --
* initialize a dump cursor.
*/
-void
-__wt_curdump_init(WT_CURSOR *cursor)
+int
+__wt_curdump_create(WT_CURSOR *child, WT_CURSOR *owner, WT_CURSOR **cursorp)
{
- cursor->get_key = __curdump_get_key;
- cursor->get_value = __curdump_get_value;
- cursor->set_key = __curdump_set_key;
- cursor->set_value = __curdump_set_value;
+ static WT_CURSOR iface = {
+ NULL,
+ NULL,
+ NULL,
+ NULL,
+ __curdump_get_key,
+ __curdump_get_value,
+ __curdump_set_key,
+ __curdump_set_value,
+ NULL,
+ __curdump_next,
+ __curdump_prev,
+ __curdump_reset,
+ __curdump_search,
+ __curdump_search_near,
+ __curdump_insert,
+ __curdump_update,
+ __curdump_remove,
+ __curdump_close,
+ { NULL, NULL }, /* TAILQ_ENTRY q */
+ 0, /* recno key */
+ { 0 }, /* recno raw buffer */
+ { NULL, 0, 0, NULL, 0 },/* WT_ITEM key */
+ { NULL, 0, 0, NULL, 0 },/* WT_ITEM value */
+ 0, /* int saved_err */
+ 0 /* uint32_t flags */
+ };
+ WT_CURSOR *cursor;
+ WT_CURSOR_DUMP *cdump;
+ WT_SESSION_IMPL *session;
+ const char *cfg[] = API_CONF_DEFAULTS(session, open_cursor, NULL);
+
+ session = (WT_SESSION_IMPL *)child->session;
+ WT_RET(__wt_calloc_def(session, 1, &cdump));
+ cursor = &cdump->iface;
+ *cursor = iface;
+ cursor->session = child->session;
+ cursor->uri = child->uri;
+ cursor->key_format = child->key_format;
+ cursor->value_format = child->value_format;
+ cdump->child = child;
+
+ /* Copy the dump flags from the child cursor. */
+ F_SET(cursor,
+ F_ISSET(child, WT_CURSTD_DUMP_PRINT | WT_CURSTD_DUMP_HEX));
+
+ WT_RET(__wt_cursor_init(cursor, NULL, owner, cfg, cursorp));
+ return (0);
}
diff --git a/src/cursor/cur_file.c b/src/cursor/cur_file.c
index 0be9eec283c..f9e9b35096f 100644
--- a/src/cursor/cur_file.c
+++ b/src/cursor/cur_file.c
@@ -261,8 +261,7 @@ __wt_curfile_create(WT_SESSION_IMPL *session,
WT_ERR(__wt_curbulk_init((WT_CURSOR_BULK *)cbt));
STATIC_ASSERT(offsetof(WT_CURSOR_BTREE, iface) == 0);
- WT_ERR(__wt_cursor_init(cursor, cursor->uri, owner, cfg));
- *cursorp = cursor;
+ WT_ERR(__wt_cursor_init(cursor, cursor->uri, owner, cfg, cursorp));
if (0) {
err: __wt_free(session, cbt);
diff --git a/src/cursor/cur_index.c b/src/cursor/cur_index.c
index 1000953fe7d..efaa8ac48b4 100644
--- a/src/cursor/cur_index.c
+++ b/src/cursor/cur_index.c
@@ -426,9 +426,7 @@ __wt_curindex_open(WT_SESSION_IMPL *session,
/* Open the column groups needed for this index cursor. */
WT_ERR(__curindex_open_colgroups(session, cindex, cfg));
-
- WT_ERR(__wt_cursor_init(cursor, cursor->uri, 0, cfg));
- *cursorp = cursor;
+ WT_ERR(__wt_cursor_init(cursor, cursor->uri, 0, cfg, cursorp));
if (0) {
err: (void)__curindex_close(cursor);
diff --git a/src/cursor/cur_stat.c b/src/cursor/cur_stat.c
index b38982069e5..dbc9d114265 100644
--- a/src/cursor/cur_stat.c
+++ b/src/cursor/cur_stat.c
@@ -386,9 +386,7 @@ __wt_curstat_open(WT_SESSION_IMPL *session,
cst->clear_func = clear_func;
STATIC_ASSERT(offsetof(WT_CURSOR_STAT, iface) == 0);
- WT_ERR(__wt_cursor_init(cursor, uri, NULL, cfg));
-
- *cursorp = cursor;
+ WT_ERR(__wt_cursor_init(cursor, uri, NULL, cfg, cursorp));
if (0) {
err: __wt_free(session, cst);
diff --git a/src/cursor/cur_std.c b/src/cursor/cur_std.c
index 562c8362419..27659070d15 100644
--- a/src/cursor/cur_std.c
+++ b/src/cursor/cur_std.c
@@ -371,12 +371,12 @@ err: if (cursor != NULL)
*/
int
__wt_cursor_init(WT_CURSOR *cursor,
- const char *uri, WT_CURSOR *owner, const char *cfg[])
+ const char *uri, WT_CURSOR *owner, const char *cfg[], WT_CURSOR **cursorp)
{
+ WT_CURSOR *cdump;
WT_CONFIG_ITEM cval;
WT_SESSION_IMPL *session;
- WT_UNUSED(cfg);
session = (WT_SESSION_IMPL *)cursor->session;
if (cursor->get_key == NULL)
@@ -407,11 +407,12 @@ __wt_cursor_init(WT_CURSOR *cursor,
WT_RET(__wt_config_gets(session, cfg, "dump", &cval));
if (cval.len != 0) {
- __wt_curdump_init(cursor);
- F_SET(cursor,
- strncmp(cval.str, "print", cval.len) == 0 ?
+ F_SET(cursor, (strncmp(cval.str, "print", cval.len) == 0) ?
WT_CURSTD_DUMP_PRINT : WT_CURSTD_DUMP_HEX);
- }
+ WT_RET(__wt_curdump_create(cursor, owner, &cdump));
+ owner = cdump;
+ } else
+ cdump = NULL;
WT_RET(__wt_config_gets(session, cfg, "raw", &cval));
if (cval.val != 0)
@@ -434,6 +435,7 @@ __wt_cursor_init(WT_CURSOR *cursor,
F_SET(cursor, WT_CURSTD_OPEN);
+ *cursorp = (cdump != NULL) ? cdump : cursor;
return (0);
}
diff --git a/src/cursor/cur_table.c b/src/cursor/cur_table.c
index b2d35d1faf9..f87edd92f34 100644
--- a/src/cursor/cur_table.c
+++ b/src/cursor/cur_table.c
@@ -598,7 +598,7 @@ __wt_curtable_open(WT_SESSION_IMPL *session,
}
STATIC_ASSERT(offsetof(WT_CURSOR_TABLE, iface) == 0);
- WT_ERR(__wt_cursor_init(cursor, cursor->uri, NULL, cfg));
+ WT_ERR(__wt_cursor_init(cursor, cursor->uri, NULL, cfg, cursorp));
/*
* Open the colgroup cursors immediately: we're going to need them for
@@ -610,10 +610,9 @@ __wt_curtable_open(WT_SESSION_IMPL *session,
*/
WT_ERR(__curtable_open_colgroups(ctable, cfg));
- *cursorp = cursor;
-
if (0) {
err: (void)__curtable_close(cursor);
+ *cursorp = NULL;
}
return (ret);
diff --git a/src/include/cursor.h b/src/include/cursor.h
index d858505a99e..6dc01a44437 100644
--- a/src/include/cursor.h
+++ b/src/include/cursor.h
@@ -120,6 +120,12 @@ struct __wt_cursor_config {
WT_CURSOR iface;
};
+struct __wt_cursor_dump {
+ WT_CURSOR iface;
+
+ WT_CURSOR *child;
+};
+
struct __wt_cursor_index {
WT_CURSOR_BTREE cbt;
diff --git a/src/include/extern.h b/src/include/extern.h
index 1b9f45a7ce9..7f9e633a702 100644
--- a/src/include/extern.h
+++ b/src/include/extern.h
@@ -455,7 +455,9 @@ extern int __wt_curconfig_open(WT_SESSION_IMPL *session,
const char *uri,
const char *cfg[],
WT_CURSOR **cursorp);
-extern void __wt_curdump_init(WT_CURSOR *cursor);
+extern int __wt_curdump_create(WT_CURSOR *child,
+ WT_CURSOR *owner,
+ WT_CURSOR **cursorp);
extern int __wt_curfile_create(WT_SESSION_IMPL *session,
WT_CURSOR *owner,
const char *cfg[],
@@ -487,7 +489,8 @@ extern int __wt_cursor_dup(WT_SESSION_IMPL *session,
extern int __wt_cursor_init(WT_CURSOR *cursor,
const char *uri,
WT_CURSOR *owner,
- const char *cfg[]);
+ const char *cfg[],
+ WT_CURSOR **cursorp);
extern int __wt_cursor_kv_not_set(WT_CURSOR *cursor, int key);
extern int __wt_curtable_get_key(WT_CURSOR *cursor, ...);
extern int __wt_curtable_get_value(WT_CURSOR *cursor, ...);
@@ -771,7 +774,7 @@ extern int __wt_btree_get_root(WT_SESSION_IMPL *session, WT_ITEM *addr);
extern int __wt_btree_free_root(WT_SESSION_IMPL *session);
extern int __wt_btree_set_root(WT_SESSION_IMPL *session,
const char *filename,
- uint8_t *addr,
+ const uint8_t *addr,
uint32_t size);
extern void __wt_eventv(WT_SESSION_IMPL *session,
int msg_event,
@@ -827,16 +830,20 @@ __wt_hazard_set(WT_SESSION_IMPL *session, WT_REF *ref
extern void __wt_hazard_clear(WT_SESSION_IMPL *session, WT_PAGE *page);
extern void __wt_hazard_empty(WT_SESSION_IMPL *session);
extern void __wt_hazard_validate(WT_SESSION_IMPL *session, WT_PAGE *page);
-extern void __wt_raw_to_hex(const void *from, void *to, uint32_t *sizep);
-extern void __wt_raw_to_esc_hex(const void *from, void *to, uint32_t *sizep);
-extern int __wt_hex_to_raw( WT_SESSION_IMPL *session,
- void *from,
- void *to,
- uint32_t *sizep);
-extern int __wt_esc_hex_to_raw( WT_SESSION_IMPL *session,
- void *from,
- void *to,
- uint32_t *sizep);
+extern int __wt_raw_to_hex(WT_SESSION_IMPL *session,
+ const uint8_t *from,
+ uint32_t size,
+ WT_ITEM *to);
+extern int __wt_raw_to_esc_hex(WT_SESSION_IMPL *session,
+ const uint8_t *from,
+ size_t size,
+ WT_ITEM *to);
+extern int __wt_hex_to_raw(WT_SESSION_IMPL *session,
+ const char *from,
+ WT_ITEM *to);
+extern int __wt_esc_hex_to_raw(WT_SESSION_IMPL *session,
+ const char *from,
+ WT_ITEM *to);
extern int __wt_huffman_open(WT_SESSION_IMPL *session,
void *symbol_frequency_array,
u_int symcnt,
diff --git a/src/include/wt_internal.in b/src/include/wt_internal.in
index 638bf79373d..803f9cf704b 100644
--- a/src/include/wt_internal.in
+++ b/src/include/wt_internal.in
@@ -86,6 +86,8 @@ struct __wt_cursor_bulk;
typedef struct __wt_cursor_bulk WT_CURSOR_BULK;
struct __wt_cursor_config;
typedef struct __wt_cursor_config WT_CURSOR_CONFIG;
+struct __wt_cursor_dump;
+ typedef struct __wt_cursor_dump WT_CURSOR_DUMP;
struct __wt_cursor_index;
typedef struct __wt_cursor_index WT_CURSOR_INDEX;
struct __wt_cursor_stat;
diff --git a/src/session/session_root.c b/src/session/session_root.c
index 4a8ec127ddf..5d7d8b76540 100644
--- a/src/session/session_root.c
+++ b/src/session/session_root.c
@@ -28,7 +28,6 @@ int
__wt_btree_get_root(WT_SESSION_IMPL *session, WT_ITEM *addr)
{
WT_BTREE *btree;
- uint32_t size;
int majorv, minorv, ret;
const char *v;
@@ -59,10 +58,8 @@ __wt_btree_get_root(WT_SESSION_IMPL *session, WT_ITEM *addr)
"%s is an unsupported version of a WiredTiger file",
btree->filename);
- if (v != NULL && strlen(v) != 0 && strcmp(v, WT_NOADDR) != 0) {
- WT_ERR(__wt_hex_to_raw(session, (void *)v, (void *)v, &size));
- WT_ERR(__wt_buf_set(session, addr, v, size));
- }
+ if (v != NULL && strlen(v) != 0 && strcmp(v, WT_NOADDR) != 0)
+ WT_ERR(__wt_hex_to_raw(session, v, addr));
err: if (ret != 0)
__wt_errx(session,
@@ -108,7 +105,7 @@ err: __wt_scr_free(&addr);
*/
int
__wt_btree_set_root(WT_SESSION_IMPL *session,
- const char *filename, uint8_t *addr, uint32_t size)
+ const char *filename, const uint8_t *addr, uint32_t size)
{
WT_ITEM *v;
int ret;
@@ -118,7 +115,7 @@ __wt_btree_set_root(WT_SESSION_IMPL *session,
/*
* Every bytes is encoded as 2 bytes, plus a trailing nul byte,
- * and it needs to hold the [NoAddr] string.
+ * and it needs to hold the "no address" string.
*/
WT_RET(__wt_scr_alloc(
session, size * 2 + 1 + WT_STORE_SIZE(strlen(WT_NOADDR)), &v));
@@ -133,11 +130,8 @@ __wt_btree_set_root(WT_SESSION_IMPL *session,
if (addr == NULL) {
v->data = WT_NOADDR;
v->size = WT_STORE_SIZE(strlen(WT_NOADDR)) + 1;
- } else {
- __wt_raw_to_hex(addr, v->mem, &size);
- v->data = v->mem;
- v->size = size;
- }
+ } else
+ WT_ERR(__wt_raw_to_hex(session, addr, size, v));
WT_ERR(strcmp(filename, WT_SCHEMA_FILENAME) == 0 ?
__btree_set_turtle(session, v) :
diff --git a/src/support/hex.c b/src/support/hex.c
index e23118d2a22..e582e9576ef 100644
--- a/src/support/hex.c
+++ b/src/support/hex.c
@@ -7,44 +7,59 @@
#include "wt_internal.h"
-static const u_char hex[] = "0123456789abcdef";
+static const char hex[] = "0123456789abcdef";
/*
* __wt_raw_to_hex --
* Convert a chunk of data to a printable hex string.
*/
-void
-__wt_raw_to_hex(const void *from, void *to, uint32_t *sizep)
+int
+__wt_raw_to_hex(WT_SESSION_IMPL *session,
+ const uint8_t *from, uint32_t size, WT_ITEM *to)
{
uint32_t i;
const uint8_t *p;
- uint8_t *t, *t_start;
+ char *t;
+
+ /*
+ * In the worst case, every character takes up 2 spaces, plus a
+ * trailing nul byte.
+ */
+ WT_RET(__wt_buf_init(session, to, size * 2 + 1));
- for (p = from, t = t_start = to, i = *sizep; i > 0; --i, ++p) {
+ for (p = from, t = to->mem, i = size; i > 0; --i, ++p) {
*t++ = hex[(*p & 0xf0) >> 4];
*t++ = hex[*p & 0x0f];
}
*t++ = '\0';
- *sizep = WT_PTRDIFF32(t, t_start);
+ to->size = WT_PTRDIFF32(t, to->mem);
+ return (0);
}
/*
* __wt_raw_to_esc_hex --
* Convert a chunk of data to an printable string using escaped hex as
- * necessary.
+ * necessary.
*/
-void
-__wt_raw_to_esc_hex(const void *from, void *to, uint32_t *sizep)
+int
+__wt_raw_to_esc_hex(WT_SESSION_IMPL *session,
+ const uint8_t *from, size_t size, WT_ITEM *to)
{
- uint32_t i;
+ size_t i;
const uint8_t *p;
- uint8_t *t, *t_start;
+ uint8_t *t;
/*
* In the worst case, every character takes up 3 spaces, plus a
* trailing nul byte.
*/
- for (p = from, t = t_start = to, i = *sizep; i > 0; --i, ++p)
+ WT_RET(__wt_buf_init(session, to, size * 3 + 1));
+
+ /*
+ * In the worst case, every character takes up 3 spaces, plus a
+ * trailing nul byte.
+ */
+ for (p = from, t = to->mem, i = size; i > 0; --i, ++p)
if (isprint((int)*p)) {
if (*p == '\\')
*t++ = '\\';
@@ -55,7 +70,8 @@ __wt_raw_to_esc_hex(const void *from, void *to, uint32_t *sizep)
*t++ = hex[*p & 0x0f];
}
*t++ = '\0';
- *sizep = WT_PTRDIFF32(t, t_start);
+ to->size = WT_PTRDIFF32(t, to->mem);
+ return (0);
}
/*
@@ -63,7 +79,7 @@ __wt_raw_to_esc_hex(const void *from, void *to, uint32_t *sizep)
* Convert a pair of hex characters into a byte.
*/
static inline int
-hex2byte(uint8_t *from, uint8_t *to)
+hex2byte(const char *from, uint8_t *to)
{
uint8_t byte;
@@ -123,34 +139,40 @@ __hex_fmterr(WT_SESSION_IMPL *session)
* Convert a printable hex string to a chunk of data.
*/
int
-__wt_hex_to_raw(
- WT_SESSION_IMPL *session, void *from, void *to, uint32_t *sizep)
+__wt_hex_to_raw(WT_SESSION_IMPL *session, const char *from, WT_ITEM *to)
{
- uint8_t *p, *t, *t_start;
+ const char *p;
+ uint8_t *t;
+ size_t size;
- if (strlen(from) % 2 != 0)
+ size = strlen(from);
+ if (size % 2 != 0)
return (__hex_fmterr(session));
- for (p = from, t = t_start = to; *p != '\0'; p += 2, ++t)
+ WT_RET(__wt_buf_init(session, to, size / 2));
+
+ for (p = from, t = to->mem; *p != '\0'; p += 2, ++t)
if (hex2byte(p, t))
return (__hex_fmterr(session));
- *sizep = WT_PTRDIFF32(t, t_start);
+ to->size = WT_PTRDIFF32(t, to->mem);
return (0);
}
/*
* __wt_esc_hex_to_raw --
* Convert a printable string using escaped hex as necessary to a chunk
- * of data.
+ * of data.
*/
int
-__wt_esc_hex_to_raw(
- WT_SESSION_IMPL *session, void *from, void *to, uint32_t *sizep)
+__wt_esc_hex_to_raw(WT_SESSION_IMPL *session, const char *from, WT_ITEM *to)
{
- uint8_t *p, *t, *t_start;
+ const char *p;
+ uint8_t *t;
+
+ WT_RET(__wt_buf_init(session, to, strlen(from)));
- for (p = from, t = t_start = to; *p != '\0'; ++p, ++t) {
+ for (p = from, t = to->mem; *p != '\0'; ++p, ++t) {
if ((*t = *p) != '\\')
continue;
++p;
@@ -160,6 +182,6 @@ __wt_esc_hex_to_raw(
++p;
}
}
- *sizep = WT_PTRDIFF32(t, t_start);
+ to->size = WT_PTRDIFF32(t, to->mem);
return (0);
}
diff --git a/src/support/scratch.c b/src/support/scratch.c
index e14b4ec2240..cd4cbb0cca6 100644
--- a/src/support/scratch.c
+++ b/src/support/scratch.c
@@ -120,19 +120,7 @@ int
__wt_buf_set_printable(
WT_SESSION_IMPL *session, WT_ITEM *buf, const void *from_arg, size_t size)
{
- uint32_t u32size;
-
- /*
- * In the worst case, every character takes up 3 spaces, plus a
- * trailing nul byte.
- */
- WT_RET(__wt_buf_init(session, buf, size * 3 + 10));
-
- u32size = (uint32_t)size;
- __wt_raw_to_esc_hex(from_arg, buf->mem, &u32size);
- buf->size = u32size;
-
- return (0);
+ return (__wt_raw_to_esc_hex(session, from_arg, size, buf));
}
/*