diff options
author | Keith Bostic <keith@wiredtiger.com> | 2016-04-22 12:34:31 -0400 |
---|---|---|
committer | Keith Bostic <keith@wiredtiger.com> | 2016-04-22 12:34:31 -0400 |
commit | ce864e99c22de1653344d4590d8aa27a40804ab7 (patch) | |
tree | 46106ff096b49b9d30405b6e515d38b0264d5e7e /src | |
parent | 3a6488a12d339b1bb8a1ff3eb015f08327be855a (diff) | |
download | mongo-ce864e99c22de1653344d4590d8aa27a40804ab7.tar.gz |
WT-2576: variable-length column-store out-of-order return
The callers of __split_multi_inmem_fail allocate WT_REF arrays, then
individual WT_REFs, check for uninitialized WT_REFs pointers.
The change to remove the record number from variable-length column-store
pages broke column-store page-rewrite: page-rewrite didn't set the
WT_REF.recno for the temporary WT_REF being used for the rewrite, so the
search routine didn't find records on the page and we ended up building
corrupt pages. Set the record number in the temporary WT_REF.
Diffstat (limited to 'src')
-rw-r--r-- | src/btree/bt_split.c | 20 |
1 files changed, 15 insertions, 5 deletions
diff --git a/src/btree/bt_split.c b/src/btree/bt_split.c index ec5843d9bf3..a668f57df62 100644 --- a/src/btree/bt_split.c +++ b/src/btree/bt_split.c @@ -1603,10 +1603,15 @@ __split_multi_inmem_fail(WT_SESSION_IMPL *session, WT_PAGE *orig, WT_REF *ref) * new pages. Discard the new allocated WT_REF structures and their * pages (setting a flag so the discard code doesn't discard the updates * on the page). + * + * Our callers allocate WT_REF arrays, then individual WT_REFs, check + * for uninitialized information. */ - if (ref->page != NULL) - F_SET_ATOMIC(ref->page, WT_PAGE_UPDATE_IGNORE); - __wt_free_ref(session, ref, orig->type, true); + if (ref != NULL) { + if (ref->page != NULL) + F_SET_ATOMIC(ref->page, WT_PAGE_UPDATE_IGNORE); + __wt_free_ref(session, ref, orig->type, true); + } } /* @@ -2180,10 +2185,15 @@ __wt_split_rewrite(WT_SESSION_IMPL *session, WT_REF *ref) * to re-create a page in memory after it's been reconciled, and that's * exactly what we want to do. * - * Build the new page. (Allocate a WT_REF because the error path uses - * routines that want to free memory). + * Build the new page. + * + * Allocate a WT_REF because the error path uses routines that will ea + * free memory. The only field we need to set is the record number, as + * it's used by the search routines. */ WT_RET(__wt_calloc_one(session, &new)); + new->ref_recno = ref->ref_recno; + WT_ERR(__split_multi_inmem(session, page, new, &mod->mod_multi[0])); /* |