summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--dist/api_data.py2
-rw-r--r--src/btree/bt_curnext.c2
-rw-r--r--src/btree/bt_curprev.c2
-rw-r--r--src/btree/bt_cursor.c2
-rw-r--r--src/btree/bt_debug.c8
-rw-r--r--src/btree/bt_page.c10
-rw-r--r--src/btree/bt_ret.c2
-rw-r--r--src/btree/bt_slvg.c12
-rw-r--r--src/btree/bt_stat.c2
-rw-r--r--src/btree/bt_vrfy.c13
-rw-r--r--src/btree/bt_vrfy_dsk.c8
-rw-r--r--src/btree/bt_walk.c2
-rw-r--r--src/btree/rec_write.c58
-rw-r--r--src/btree/row_key.c6
-rw-r--r--src/docs/upgrading.dox11
-rw-r--r--src/include/btree.i4
-rw-r--r--src/include/cell.i74
-rw-r--r--src/include/cursor.i6
18 files changed, 127 insertions, 97 deletions
diff --git a/dist/api_data.py b/dist/api_data.py
index 11aae5a61f2..a62d6ae85cd 100644
--- a/dist/api_data.py
+++ b/dist/api_data.py
@@ -232,7 +232,7 @@ file_config = format_meta + [
written into the buffer cache''',
min=0),
Config('prefix_compression', 'true', r'''
- configure row-store format key prefix compression''',
+ configure prefix compression on row-store leaf pages''',
type='boolean'),
Config('split_pct', '75', r'''
the Btree page split size as a percentage of the maximum Btree
diff --git a/src/btree/bt_curnext.c b/src/btree/bt_curnext.c
index f50070e1dcb..97fe71dba63 100644
--- a/src/btree/bt_curnext.c
+++ b/src/btree/bt_curnext.c
@@ -217,7 +217,7 @@ new_page: /* Find the matching WT_COL slot. */
if (cbt->cip_saved != cip) {
if ((cell = WT_COL_PTR(cbt->page, cip)) == NULL)
continue;
- __wt_cell_unpack(cell, &unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, &unpack);
if (unpack.type == WT_CELL_DEL)
continue;
diff --git a/src/btree/bt_curprev.c b/src/btree/bt_curprev.c
index aa99ff985d8..0b7e1c57fb6 100644
--- a/src/btree/bt_curprev.c
+++ b/src/btree/bt_curprev.c
@@ -353,7 +353,7 @@ new_page: if (cbt->recno < cbt->page->u.col_var.recno)
if (cbt->cip_saved != cip) {
if ((cell = WT_COL_PTR(cbt->page, cip)) == NULL)
continue;
- __wt_cell_unpack(cell, &unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, &unpack);
if (unpack.type == WT_CELL_DEL)
continue;
diff --git a/src/btree/bt_cursor.c b/src/btree/bt_cursor.c
index d09edd50934..c1bc3f0fd49 100644
--- a/src/btree/bt_cursor.c
+++ b/src/btree/bt_cursor.c
@@ -87,7 +87,7 @@ __cursor_invalid(WT_CURSOR_BTREE *cbt)
cip = &page->u.col_var.d[cbt->slot];
if ((cell = WT_COL_PTR(page, cip)) == NULL)
return (WT_NOTFOUND);
- __wt_cell_unpack(cell, &unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, &unpack);
if (unpack.type == WT_CELL_DEL)
return (1);
break;
diff --git a/src/btree/bt_debug.c b/src/btree/bt_debug.c
index 3c20ece633f..be2b1261e7e 100644
--- a/src/btree/bt_debug.c
+++ b/src/btree/bt_debug.c
@@ -316,7 +316,7 @@ __debug_dsk_cell(WT_DBG *ds, WT_PAGE_HEADER *dsk)
unpack = &_unpack;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, dsk->type, unpack);
WT_RET(__debug_cell(ds, dsk, unpack));
}
return (0);
@@ -644,7 +644,7 @@ __debug_page_col_var(WT_DBG *ds, WT_PAGE *page)
unpack = NULL;
rle = 1;
} else {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, unpack);
rle = __wt_cell_rle(unpack);
}
snprintf(tag, sizeof(tag), "%" PRIu64 " %" PRIu64, recno, rle);
@@ -717,14 +717,14 @@ __debug_page_row_leaf(WT_DBG *ds, WT_PAGE *page)
if (__wt_off_page(page, ripkey))
__debug_ikey(ds, ripkey);
else {
- __wt_cell_unpack(ripkey, unpack);
+ __wt_cell_unpack(ripkey, WT_PAGE_ROW_LEAF, unpack);
WT_RET(__debug_cell_data(ds, "K", unpack));
}
if ((cell = __wt_row_value(page, rip)) == NULL)
__dmsg(ds, "\tV {}\n");
else {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_LEAF, unpack);
WT_RET(__debug_cell_data(ds, "V", unpack));
}
diff --git a/src/btree/bt_page.c b/src/btree/bt_page.c
index 43c3ec277ae..62e66dff8ae 100644
--- a/src/btree/bt_page.c
+++ b/src/btree/bt_page.c
@@ -343,7 +343,7 @@ __inmem_col_int(WT_SESSION_IMPL *session, WT_PAGE *page)
*/
ref = page->u.intl.t;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_INT, unpack);
ref->addr = cell;
ref->u.recno = unpack->v;
++ref;
@@ -383,7 +383,7 @@ __inmem_col_var(WT_SESSION_IMPL *session, WT_PAGE *page, size_t *sizep)
indx = 0;
cip = page->u.col_var.d;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, unpack);
(cip++)->__value = WT_PAGE_DISK_OFFSET(page, cell);
/*
@@ -442,7 +442,7 @@ __inmem_row_int(WT_SESSION_IMPL *session, WT_PAGE *page, size_t *sizep)
*/
ref = page->u.intl.t;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_INT, unpack);
switch (unpack->type) {
case WT_CELL_KEY:
case WT_CELL_KEY_OVFL:
@@ -585,7 +585,7 @@ __inmem_row_leaf_entries(
*/
nindx = 0;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_LEAF, unpack);
switch (unpack->type) {
case WT_CELL_KEY:
case WT_CELL_KEY_OVFL:
@@ -631,7 +631,7 @@ __inmem_row_leaf(WT_SESSION_IMPL *session, WT_PAGE *page)
/* Walk the page, building indices. */
rip = page->u.row.d;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_LEAF, unpack);
switch (unpack->type) {
case WT_CELL_KEY:
case WT_CELL_KEY_OVFL:
diff --git a/src/btree/bt_ret.c b/src/btree/bt_ret.c
index b71166d4b6f..09e07050d80 100644
--- a/src/btree/bt_ret.c
+++ b/src/btree/bt_ret.c
@@ -104,7 +104,7 @@ __wt_kv_return(WT_SESSION_IMPL *session, WT_CURSOR_BTREE *cbt)
}
/* The value is an on-page cell, unpack and expand it as necessary. */
- __wt_cell_unpack(cell, &unpack);
+ __wt_cell_unpack(cell, page->type, &unpack);
ret = __wt_cell_unpack_ref(session, &unpack, &cursor->value);
/*
diff --git a/src/btree/bt_slvg.c b/src/btree/bt_slvg.c
index 79c74a5f0ad..f371b83d430 100644
--- a/src/btree/bt_slvg.c
+++ b/src/btree/bt_slvg.c
@@ -507,7 +507,7 @@ __slvg_trk_leaf(WT_SESSION_IMPL *session,
*/
stop_recno = dsk->recno;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, unpack);
stop_recno += __wt_cell_rle(unpack);
}
@@ -616,7 +616,7 @@ __slvg_trk_leaf_ovfl(
*/
ovfl_cnt = 0;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, dsk->type, unpack);
if (unpack->ovfl)
++ovfl_cnt;
}
@@ -628,7 +628,7 @@ __slvg_trk_leaf_ovfl(
ovfl_cnt = 0;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, dsk->type, unpack);
if (unpack->ovfl) {
WT_RET(__wt_strndup(session, unpack->data,
unpack->size, &trk->ovfl[ovfl_cnt].addr));
@@ -1252,7 +1252,7 @@ __slvg_col_merge_ovfl(WT_SESSION_IMPL *session,
WT_COL_FOREACH(page, cip, i) {
cell = WT_COL_PTR(page, cip);
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, unpack);
recno += __wt_cell_rle(unpack);
if (unpack->type != WT_CELL_VALUE_OVFL)
@@ -1904,7 +1904,7 @@ __slvg_row_merge_ovfl(WT_SESSION_IMPL *session,
cell = WT_PAGE_REF_OFFSET(page, ikey->cell_offset);
else
cell = (WT_CELL *)ikey;
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_LEAF, unpack);
if (unpack->type == WT_CELL_KEY_OVFL) {
WT_VERBOSE_RET(session, salvage,
"%s merge discard freed overflow reference %s",
@@ -1919,7 +1919,7 @@ __slvg_row_merge_ovfl(WT_SESSION_IMPL *session,
if ((cell = __wt_row_value(page, rip)) == NULL)
continue;
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_LEAF, unpack);
if (unpack->type == WT_CELL_VALUE_OVFL) {
WT_VERBOSE_RET(session, salvage,
"%s merge discard freed overflow reference %s",
diff --git a/src/btree/bt_stat.c b/src/btree/bt_stat.c
index ee5163c5cd9..1238a56a4ae 100644
--- a/src/btree/bt_stat.c
+++ b/src/btree/bt_stat.c
@@ -117,7 +117,7 @@ __stat_page_col_var(
WT_STAT_INCR(session, stats, btree_column_deleted);
} else {
orig_deleted = 0;
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, unpack);
WT_STAT_INCRV(session,
stats, btree_entries, __wt_cell_rle(unpack));
}
diff --git a/src/btree/bt_vrfy.c b/src/btree/bt_vrfy.c
index 7c68d1b86d8..aa657d79241 100644
--- a/src/btree/bt_vrfy.c
+++ b/src/btree/bt_vrfy.c
@@ -289,7 +289,7 @@ recno_chk: if (recno != vs->record_total + 1)
if ((cell = WT_COL_PTR(page, cip)) == NULL)
++recno;
else {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, unpack);
recno += __wt_cell_rle(unpack);
}
vs->record_total += recno;
@@ -321,7 +321,7 @@ recno_chk: if (recno != vs->record_total + 1)
if (WT_PAGE_IS_ROOT(page))
lno = 0;
else {
- __wt_cell_unpack(page->ref->addr, unpack);
+ __wt_cell_unpack(page->ref->addr, page->type, unpack);
lno = unpack->raw == WT_CELL_ADDR_LNO ? 1 : 0;
}
switch (page->type) {
@@ -362,7 +362,8 @@ recno_chk: if (recno != vs->record_total + 1)
*/
++entry;
if (ref->u.recno != vs->record_total + 1) {
- __wt_cell_unpack(ref->addr, unpack);
+ __wt_cell_unpack(
+ ref->addr, WT_PAGE_COL_INT, unpack);
WT_RET_MSG(session, WT_ERROR,
"the starting record number in entry %"
PRIu32 " of the column internal page at "
@@ -381,7 +382,7 @@ recno_chk: if (recno != vs->record_total + 1)
WT_TRET(__wt_page_release(session, ref->page));
WT_RET(ret);
- __wt_cell_unpack(ref->addr, unpack);
+ __wt_cell_unpack(ref->addr, WT_PAGE_COL_INT, unpack);
WT_RET(bm->verify_addr(
bm, session, unpack->data, unpack->size));
}
@@ -409,7 +410,7 @@ recno_chk: if (recno != vs->record_total + 1)
WT_TRET(__wt_page_release(session, ref->page));
WT_RET(ret);
- __wt_cell_unpack(ref->addr, unpack);
+ __wt_cell_unpack(ref->addr, WT_PAGE_ROW_INT, unpack);
WT_RET(bm->verify_addr(
bm, session, unpack->data, unpack->size));
}
@@ -549,7 +550,7 @@ __verify_overflow_cell(
cell_num = 0;
WT_CELL_FOREACH(btree, dsk, cell, unpack, i) {
++cell_num;
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, dsk->type, unpack);
switch (unpack->type) {
case WT_CELL_KEY_OVFL:
case WT_CELL_VALUE_OVFL:
diff --git a/src/btree/bt_vrfy_dsk.c b/src/btree/bt_vrfy_dsk.c
index 3eec747e53e..9456b046374 100644
--- a/src/btree/bt_vrfy_dsk.c
+++ b/src/btree/bt_vrfy_dsk.c
@@ -174,7 +174,7 @@ __verify_dsk_row(
++cell_num;
/* Carefully unpack the cell. */
- if (__wt_cell_unpack_safe(cell, unpack, end) != 0) {
+ if (__wt_cell_unpack_safe(cell, dsk->type, unpack, end) != 0) {
ret = __err_cell_corrupted(session, cell_num, addr);
goto err;
}
@@ -399,7 +399,8 @@ __verify_dsk_col_int(
++cell_num;
/* Carefully unpack the cell. */
- if (__wt_cell_unpack_safe(cell, unpack, end) != 0)
+ if (__wt_cell_unpack_safe(
+ cell, WT_PAGE_COL_INT, unpack, end) != 0)
return (__err_cell_corrupted(session, cell_num, addr));
/* Check the raw and collapsed cell types. */
@@ -464,7 +465,8 @@ __verify_dsk_col_var(
++cell_num;
/* Carefully unpack the cell. */
- if (__wt_cell_unpack_safe(cell, unpack, end) != 0)
+ if (__wt_cell_unpack_safe(
+ cell, WT_PAGE_COL_VAR, unpack, end) != 0)
return (__err_cell_corrupted(session, cell_num, addr));
/* Check the raw and collapsed cell types. */
diff --git a/src/btree/bt_walk.c b/src/btree/bt_walk.c
index dd94b8ab846..b1f3ef21fe2 100644
--- a/src/btree/bt_walk.c
+++ b/src/btree/bt_walk.c
@@ -89,7 +89,7 @@ __tree_walk_delete(
* locked down, instantiating the page in memory and modifying it could
* theoretically point the address somewhere away from the on-page cell.
*/
- __wt_cell_unpack(ref->addr, &unpack);
+ __wt_cell_unpack(ref->addr, page->type, &unpack);
if (unpack.raw != WT_CELL_ADDR_LNO)
goto err;
diff --git a/src/btree/rec_write.c b/src/btree/rec_write.c
index 9e3259c0453..99659ad2707 100644
--- a/src/btree/rec_write.c
+++ b/src/btree/rec_write.c
@@ -491,9 +491,12 @@ __rec_write_init(
btree->internal_key_truncate && !r->raw_compression)
r->key_sfx_compress_conf = 1;
- /* Prefix compression discards key's repeated prefix bytes. */
+ /*
+ * Prefix compression discards repeated prefix bytes from row-store leaf
+ * page keys.
+ */
r->key_pfx_compress_conf = 0;
- if (btree->prefix_compression)
+ if (btree->prefix_compression && page->type == WT_PAGE_ROW_LEAF)
r->key_pfx_compress_conf = 1;
/*
@@ -1192,7 +1195,7 @@ __rec_split_row_promote_cell(
* the first cell on a page cannot refer an earlier cell on the page.
*/
cell = WT_PAGE_HEADER_BYTE(btree, dsk);
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, dsk->type, unpack);
WT_ASSERT(session,
unpack->prefix == 0 && unpack->raw != WT_CELL_VALUE_COPY);
@@ -1502,7 +1505,7 @@ __rec_split_raw_worker(WT_SESSION_IMPL *session, WT_RECONCILE *r, int final)
* Row-store pages can split at keys, but not at values,
* column-store pages can split at values.
*/
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, dsk->type, unpack);
switch (unpack->type) {
case WT_CELL_KEY:
case WT_CELL_KEY_OVFL:
@@ -2276,7 +2279,7 @@ __rec_col_merge(WT_SESSION_IMPL *session, WT_RECONCILE *r, WT_PAGE *page)
if (addr == NULL && __wt_off_page(page, ref->addr))
addr = ref->addr;
if (addr == NULL) {
- __wt_cell_unpack(ref->addr, unpack);
+ __wt_cell_unpack(ref->addr, WT_PAGE_COL_INT, unpack);
val->buf.data = ref->addr;
val->buf.size = __wt_cell_total_len(unpack);
val->cell_len = 0;
@@ -2609,7 +2612,7 @@ __rec_col_var(WT_SESSION_IMPL *session,
ins = NULL;
orig_deleted = 1;
} else {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_COL_VAR, unpack);
nrepeat = __wt_cell_rle(unpack);
ins = WT_SKIP_FIRST(WT_COL_UPDATE(page, cip));
@@ -2942,7 +2945,7 @@ __rec_row_int(WT_SESSION_IMPL *session, WT_RECONCILE *r, WT_PAGE *page)
cell = NULL;
else {
cell = WT_PAGE_REF_OFFSET(page, ikey->cell_offset);
- __wt_cell_unpack(cell, kpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_INT, kpack);
}
/*
@@ -3041,7 +3044,7 @@ __rec_row_int(WT_SESSION_IMPL *session, WT_RECONCILE *r, WT_PAGE *page)
vtype = addr->leaf_no_overflow ?
WT_CELL_ADDR_LNO : WT_CELL_ADDR;
} else {
- __wt_cell_unpack(ref->addr, vpack);
+ __wt_cell_unpack(ref->addr, WT_PAGE_ROW_INT, vpack);
p = vpack->data;
size = vpack->size;
if (vtype == 0)
@@ -3096,19 +3099,6 @@ __rec_row_int(WT_SESSION_IMPL *session, WT_RECONCILE *r, WT_PAGE *page)
onpage_ovfl = 0;
}
WT_RET(__rec_split(session, r));
-
- /*
- * Turn off prefix compression until a full key written
- * to the new page, and (unless we're already working
- * with an overflow key), rebuild the key without prefix
- * compression.
- */
- if (r->key_pfx_compress_conf) {
- r->key_pfx_compress = 0;
- if (!ovfl_key)
- WT_RET(__rec_cell_build_key(
- session, r, NULL, 0, 1, &ovfl_key));
- }
}
/* Copy the key and value onto the page. */
@@ -3201,7 +3191,7 @@ __rec_row_merge(WT_SESSION_IMPL *session, WT_RECONCILE *r, WT_PAGE *page)
vtype = addr->leaf_no_overflow ?
WT_CELL_ADDR_LNO : WT_CELL_ADDR;
} else {
- __wt_cell_unpack(ref->addr, vpack);
+ __wt_cell_unpack(ref->addr, WT_PAGE_ROW_INT, vpack);
p = vpack->data;
size = vpack->size;
if (vtype == 0)
@@ -3227,19 +3217,6 @@ __rec_row_merge(WT_SESSION_IMPL *session, WT_RECONCILE *r, WT_PAGE *page)
continue;
}
WT_RET(__rec_split(session, r));
-
- /*
- * Turn off prefix compression until a full key written
- * to the new page, and (unless we're already working
- * with an overflow key), rebuild the key without prefix
- * compression.
- */
- if (r->key_pfx_compress_conf) {
- r->key_pfx_compress = 0;
- if (!ovfl_key)
- WT_RET(__rec_cell_build_key(
- session, r, NULL, 0, 1, &ovfl_key));
- }
}
/* Copy the key and value onto the page. */
@@ -3332,7 +3309,7 @@ __rec_row_leaf(WT_SESSION_IMPL *session,
/* Build value cell. */
dictionary = 0;
if ((val_cell = __wt_row_value(page, rip)) != NULL)
- __wt_cell_unpack(val_cell, unpack);
+ __wt_cell_unpack(val_cell, WT_PAGE_ROW_LEAF, unpack);
WT_ERR(
__rec_txn_read(session, r, WT_ROW_UPDATE(page, rip), &upd));
if (upd == NULL) {
@@ -3403,7 +3380,8 @@ __rec_row_leaf(WT_SESSION_IMPL *session,
* if an overflow key was never instantiated,
* do it now.
*/
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(
+ cell, WT_PAGE_ROW_LEAF, unpack);
if (unpack->ovfl) {
if (ikey == NULL)
WT_ERR(__wt_row_key_copy(
@@ -3446,7 +3424,7 @@ __rec_row_leaf(WT_SESSION_IMPL *session,
* overflow key blocks have been freed, we have to build a new
* key. If there's no tracking entry, use the original blocks.
*/
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_LEAF, unpack);
onpage_ovfl = unpack->ovfl;
if (onpage_ovfl &&
__wt_rec_track_onpage_srch(
@@ -4267,7 +4245,9 @@ __rec_cell_build_key(WT_SESSION_IMPL *session, WT_RECONCILE *r,
session, r, NULL, 0, is_internal, is_ovflp));
}
- key->cell_len = __wt_cell_pack_key(&key->cell, pfx, key->buf.size);
+ key->cell_len = is_internal ?
+ __wt_cell_pack_int_key(&key->cell, key->buf.size) :
+ __wt_cell_pack_leaf_key(&key->cell, pfx, key->buf.size);
key->len = key->cell_len + key->buf.size;
return (0);
diff --git a/src/btree/row_key.c b/src/btree/row_key.c
index 1142bffbdcc..9849c745055 100644
--- a/src/btree/row_key.c
+++ b/src/btree/row_key.c
@@ -172,7 +172,7 @@ __wt_row_key_copy(
__wt_cell_unpack(
WT_PAGE_REF_OFFSET(page, ikey->cell_offset),
- unpack);
+ page->type, unpack);
/*
* If we wanted a different key and this key is an
@@ -205,7 +205,7 @@ __wt_row_key_copy(
}
/* Unpack the key's cell. */
- __wt_cell_unpack(key, unpack);
+ __wt_cell_unpack(key, page->type, unpack);
/* 2: the test for an on-page reference to an overflow key. */
if (unpack->type == WT_CELL_KEY_OVFL) {
@@ -370,7 +370,7 @@ __wt_row_value(WT_PAGE *page, WT_ROW *rip)
* the length of the cell should be the byte immediately after the page
* disk image.
*/
- __wt_cell_unpack(cell, &unpack);
+ __wt_cell_unpack(cell, page->type, &unpack);
cell = (WT_CELL *)((uint8_t *)cell + __wt_cell_total_len(&unpack));
if (__wt_off_page(page, cell))
return (NULL);
diff --git a/src/docs/upgrading.dox b/src/docs/upgrading.dox
index bc49336c5c7..3f8de8a8549 100644
--- a/src/docs/upgrading.dox
+++ b/src/docs/upgrading.dox
@@ -1,5 +1,16 @@
/*! @page upgrading Upgrading WiredTiger applications
+@section version_164 Upgrading to Version 1.6.4
+<dl>
+
+<dt>File format changes</dt>
+<dd>
+The underlying file formats changed in the 1.6.4 release; tables and files
+should be dumped and re-loaded into a new database.
+</dd>
+
+</dl>
+<hr>
@section version_163 Upgrading to Version 1.6.3
<dl>
diff --git a/src/include/btree.i b/src/include/btree.i
index 3d49972043f..d86a25a08b0 100644
--- a/src/include/btree.i
+++ b/src/include/btree.i
@@ -377,7 +377,7 @@ retry: ikey = WT_ROW_KEY_COPY(rip);
/* If the key isn't compressed or an overflow, take it from the page. */
if (btree->huffman_key == NULL)
- __wt_cell_unpack((WT_CELL *)ikey, &unpack);
+ __wt_cell_unpack((WT_CELL *)ikey, page->type, &unpack);
if (btree->huffman_key == NULL &&
unpack.type == WT_CELL_KEY && unpack.prefix == 0) {
key->data = unpack.data;
@@ -422,7 +422,7 @@ __wt_get_addr(
*addrp = ((WT_ADDR *)(ref->addr))->addr;
*sizep = ((WT_ADDR *)(ref->addr))->size;
} else {
- __wt_cell_unpack(ref->addr, unpack);
+ __wt_cell_unpack(ref->addr, page->type, unpack);
*addrp = unpack->data;
*sizep = unpack->size;
}
diff --git a/src/include/cell.i b/src/include/cell.i
index a16db71819d..15a13064930 100644
--- a/src/include/cell.i
+++ b/src/include/cell.i
@@ -30,8 +30,8 @@
* Keys with optional data cells (a WT_CELL_KEY or WT_CELL_KEY_OVFL cell,
* optionally followed by a WT_CELL_{VALUE,VALUE_COPY,VALUE_OVFL} cell).
*
- * Both WT_PAGE_ROW_INT and WT_PAGE_ROW_LEAF pages prefix compress keys, using
- * a single byte immediately following the cell.
+ * WT_PAGE_ROW_LEAF pages prefix compress keys, using a single byte count
+ * immediately following the cell.
*
* WT_PAGE_COL_INT (Column-store internal page):
* Off-page references (a WT_CELL_{ADDR,ADDR_LNO} cell).
@@ -298,11 +298,41 @@ __wt_cell_pack_del(WT_CELL *cell, uint64_t rle)
}
/*
- * __wt_cell_pack_key --
- * Set a key's WT_CELL contents.
+ * __wt_cell_pack_int_key --
+ * Set a row-store internal page key's WT_CELL contents.
*/
static inline uint32_t
-__wt_cell_pack_key(WT_CELL *cell, uint8_t prefix, uint32_t size)
+__wt_cell_pack_int_key(WT_CELL *cell, uint32_t size)
+{
+ uint8_t byte, *p;
+
+ /*
+ * Short keys have 6-bits of length in the descriptor byte and no length
+ * bytes.
+ *
+ * Bit 0 is 0, bit 1 is the WT_CELL_KEY_SHORT flag; the other 6 bits are
+ * the size.
+ */
+ if (size <= 0x3f) {
+ byte = (uint8_t)size;
+ cell->__chunk[0] = (byte << 2) | WT_CELL_KEY_SHORT;
+ return (1);
+ }
+
+ cell->__chunk[0] = WT_CELL_KEY; /* Type */
+
+ p = cell->__chunk + 1; /* Length */
+ (void)__wt_vpack_uint(&p, 0, (uint64_t)size);
+
+ return (WT_PTRDIFF32(p, cell));
+}
+
+/*
+ * __wt_cell_pack_leaf_key --
+ * Set a row-store leaf page key's WT_CELL contents.
+ */
+static inline uint32_t
+__wt_cell_pack_leaf_key(WT_CELL *cell, uint8_t prefix, uint32_t size)
{
uint8_t byte, *p;
@@ -446,7 +476,8 @@ __wt_cell_type_raw(WT_CELL *cell)
* Unpack a WT_CELL into a structure during verification.
*/
static inline int
-__wt_cell_unpack_safe(WT_CELL *cell, WT_CELL_UNPACK *unpack, uint8_t *end)
+__wt_cell_unpack_safe(
+ WT_CELL *cell, int type, WT_CELL_UNPACK *unpack, uint8_t *end)
{
uint64_t v;
const uint8_t *p;
@@ -506,14 +537,21 @@ restart:
switch (unpack->raw) {
case WT_CELL_KEY_SHORT:
/*
- * Check the prefix byte that follows the cell descriptor byte.
+ * Check the prefix byte that follows the cell descriptor byte
+ * on row-store leaf pages.
*/
- WT_CELL_LEN_CHK(cell, 1);
- unpack->prefix = cell->__chunk[1];
-
- unpack->data = cell->__chunk + 2;
- unpack->size = cell->__chunk[0] >> 2;
- unpack->__len = 2 + unpack->size;
+ if (type == WT_PAGE_ROW_LEAF) {
+ WT_CELL_LEN_CHK(cell, 1);
+ unpack->prefix = cell->__chunk[1];
+
+ unpack->data = cell->__chunk + 2;
+ unpack->size = cell->__chunk[0] >> 2;
+ unpack->__len = 2 + unpack->size;
+ } else {
+ unpack->data = cell->__chunk + 1;
+ unpack->size = cell->__chunk[0] >> 2;
+ unpack->__len = 1 + unpack->size;
+ }
goto done;
case WT_CELL_VALUE_SHORT:
/*
@@ -532,10 +570,8 @@ restart:
*/
p = (uint8_t *)cell + 1; /* skip cell */
- if (unpack->raw == WT_CELL_KEY) {
- /*
- * Check the prefix byte that follows the cell descriptor byte.
- */
+ /* Check the prefix byte that follows the cell descriptor byte. */
+ if (unpack->raw == WT_CELL_KEY && type == WT_PAGE_ROW_LEAF) {
++p; /* skip prefix */
WT_CELL_LEN_CHK(p, 0);
unpack->prefix = cell->__chunk[1];
@@ -614,9 +650,9 @@ done: WT_CELL_LEN_CHK(cell, unpack->__len);
* Unpack a WT_CELL into a structure.
*/
static inline void
-__wt_cell_unpack(WT_CELL *cell, WT_CELL_UNPACK *unpack)
+__wt_cell_unpack(WT_CELL *cell, int type, WT_CELL_UNPACK *unpack)
{
- (void)__wt_cell_unpack_safe(cell, unpack, NULL);
+ (void)__wt_cell_unpack_safe(cell, type, unpack, NULL);
}
/*
diff --git a/src/include/cursor.i b/src/include/cursor.i
index 32d06d712fd..527250dda98 100644
--- a/src/include/cursor.i
+++ b/src/include/cursor.i
@@ -159,7 +159,7 @@ __cursor_func_resolve(WT_CURSOR_BTREE *cbt, int ret)
/*
* __cursor_row_slot_return --
- * Return a WT_ROW slot's K/V pair.
+ * Return a row-store leaf page slot's K/V pair.
*/
static inline int
__cursor_row_slot_return(WT_CURSOR_BTREE *cbt, WT_ROW *rip, WT_UPDATE *upd)
@@ -209,7 +209,7 @@ __cursor_row_slot_return(WT_CURSOR_BTREE *cbt, WT_ROW *rip, WT_UPDATE *upd)
*/
if (btree->huffman_key != NULL)
goto slow;
- __wt_cell_unpack((WT_CELL *)ikey, unpack);
+ __wt_cell_unpack((WT_CELL *)ikey, WT_PAGE_ROW_LEAF, unpack);
if (unpack->type == WT_CELL_KEY && unpack->prefix == 0) {
kb->data = cbt->tmp.data = unpack->data;
kb->size = cbt->tmp.size = unpack->size;
@@ -258,7 +258,7 @@ slow: WT_RET(__wt_row_key_copy(session, cbt->page, rip, kb));
vb->data = "";
vb->size = 0;
} else {
- __wt_cell_unpack(cell, unpack);
+ __wt_cell_unpack(cell, WT_PAGE_ROW_LEAF, unpack);
WT_RET(__wt_cell_unpack_ref(session, unpack, vb));
}