diff options
author | Sulabh Mahajan <sulabh.mahajan@mongodb.com> | 2016-11-15 17:03:00 +1100 |
---|---|---|
committer | Michael Cahill <michael.cahill@mongodb.com> | 2016-11-15 17:03:00 +1100 |
commit | 56f14ea2ea83b871ebaabdd0c0ff14b1dba21644 (patch) | |
tree | 72e8ed7fe96be168ab849c943803405dc634729d | |
parent | e11d885f11fc7c47f1a9160087f738da80567ad2 (diff) | |
download | mongo-56f14ea2ea83b871ebaabdd0c0ff14b1dba21644.tar.gz |
WT-3022 Change lsm_tree flags to fields to prevent race conditions (#3148)
-rw-r--r-- | src/include/lsm.h | 24 | ||||
-rw-r--r-- | src/lsm/lsm_cursor.c | 8 | ||||
-rw-r--r-- | src/lsm/lsm_merge.c | 8 | ||||
-rw-r--r-- | src/lsm/lsm_tree.c | 4 | ||||
-rw-r--r-- | src/lsm/lsm_work_unit.c | 4 |
5 files changed, 26 insertions, 22 deletions
diff --git a/src/include/lsm.h b/src/include/lsm.h index b433e4c3c44..fefed9daa81 100644 --- a/src/include/lsm.h +++ b/src/include/lsm.h @@ -249,17 +249,21 @@ struct __wt_lsm_tree { int64_t lsm_merge_throttle; /* - * The tree is open for business. This used to be a flag, but it is - * susceptible to races. + * Following fields used to be flags but are susceptible to races. + * Don't merge them with flags. */ - bool active; - -#define WT_LSM_TREE_AGGRESSIVE_TIMER 0x01 /* Timer for merge aggression */ -#define WT_LSM_TREE_COMPACTING 0x02 /* Tree being compacted */ -#define WT_LSM_TREE_MERGES 0x04 /* Tree should run merges */ -#define WT_LSM_TREE_NEED_SWITCH 0x08 /* New chunk needs creating */ -#define WT_LSM_TREE_OPEN 0x10 /* The tree is open */ -#define WT_LSM_TREE_THROTTLE 0x20 /* Throttle updates */ + bool active; /* The tree is open for business */ + bool aggressive_timer_enabled; /* Timer for merge aggression enabled */ + bool need_switch; /* New chunk needs creating */ + + /* + * flags here are not protected for concurrent access, don't put + * anything here that is susceptible to races. + */ +#define WT_LSM_TREE_COMPACTING 0x01 /* Tree being compacted */ +#define WT_LSM_TREE_MERGES 0x02 /* Tree should run merges */ +#define WT_LSM_TREE_OPEN 0x04 /* The tree is open */ +#define WT_LSM_TREE_THROTTLE 0x08 /* Throttle updates */ uint32_t flags; }; diff --git a/src/lsm/lsm_cursor.c b/src/lsm/lsm_cursor.c index c40f0f64b33..9c124885086 100644 --- a/src/lsm/lsm_cursor.c +++ b/src/lsm/lsm_cursor.c @@ -34,7 +34,7 @@ __wt_clsm_request_switch(WT_CURSOR_LSM *clsm) lsm_tree = clsm->lsm_tree; session = (WT_SESSION_IMPL *)clsm->iface.session; - if (!F_ISSET(lsm_tree, WT_LSM_TREE_NEED_SWITCH)) { + if (!lsm_tree->need_switch) { /* * Check that we are up-to-date: don't set the switch if the * tree has changed since we last opened cursors: that can lead @@ -44,8 +44,8 @@ __wt_clsm_request_switch(WT_CURSOR_LSM *clsm) __wt_lsm_tree_readlock(session, lsm_tree); if (lsm_tree->nchunks == 0 || (clsm->dsk_gen == lsm_tree->dsk_gen && - !F_ISSET(lsm_tree, WT_LSM_TREE_NEED_SWITCH))) { - F_SET(lsm_tree, WT_LSM_TREE_NEED_SWITCH); + !lsm_tree->need_switch)) { + lsm_tree->need_switch = true; ret = __wt_lsm_manager_push_entry( session, WT_LSM_WORK_SWITCH, 0, lsm_tree); } @@ -129,7 +129,7 @@ __clsm_enter_update(WT_CURSOR_LSM *clsm) * chunk grows twice as large as the configured size, block until it * can be switched. */ - hard_limit = F_ISSET(lsm_tree, WT_LSM_TREE_NEED_SWITCH); + hard_limit = lsm_tree->need_switch; if (have_primary) { WT_ENTER_PAGE_INDEX(session); diff --git a/src/lsm/lsm_merge.c b/src/lsm/lsm_merge.c index 493855d489a..dc47d0118a2 100644 --- a/src/lsm/lsm_merge.c +++ b/src/lsm/lsm_merge.c @@ -46,7 +46,7 @@ __wt_lsm_merge_update_tree(WT_SESSION_IMPL *session, static void __lsm_merge_aggressive_clear(WT_LSM_TREE *lsm_tree) { - F_CLR(lsm_tree, WT_LSM_TREE_AGGRESSIVE_TIMER); + lsm_tree->aggressive_timer_enabled = false; lsm_tree->merge_aggressiveness = 0; } @@ -85,12 +85,12 @@ __lsm_merge_aggressive_update(WT_SESSION_IMPL *session, WT_LSM_TREE *lsm_tree) } /* - * Start the timer if it isn't running. Use a flag to define whether + * Start the timer if it isn't running. Use a bool to define whether * the timer is running - since clearing and checking a special * timer value isn't simple. */ - if (!F_ISSET(lsm_tree, WT_LSM_TREE_AGGRESSIVE_TIMER)) { - F_SET(lsm_tree, WT_LSM_TREE_AGGRESSIVE_TIMER); + if (!lsm_tree->aggressive_timer_enabled) { + lsm_tree->aggressive_timer_enabled = true; __wt_epoch(session, &lsm_tree->merge_aggressive_ts); } diff --git a/src/lsm/lsm_tree.c b/src/lsm/lsm_tree.c index 0054dcd1583..714007cda98 100644 --- a/src/lsm/lsm_tree.c +++ b/src/lsm/lsm_tree.c @@ -736,7 +736,7 @@ __wt_lsm_tree_switch(WT_SESSION_IMPL *session, WT_LSM_TREE *lsm_tree) if (!first_switch && (last_chunk = lsm_tree->chunk[nchunks - 1]) != NULL && !F_ISSET(last_chunk, WT_LSM_CHUNK_ONDISK) && - !F_ISSET(lsm_tree, WT_LSM_TREE_NEED_SWITCH)) + !lsm_tree->need_switch) goto err; /* Update the throttle time. */ @@ -759,7 +759,7 @@ __wt_lsm_tree_switch(WT_SESSION_IMPL *session, WT_LSM_TREE *lsm_tree) WT_ERR(__wt_lsm_tree_setup_chunk(session, lsm_tree, chunk)); WT_ERR(__wt_lsm_meta_write(session, lsm_tree)); - F_CLR(lsm_tree, WT_LSM_TREE_NEED_SWITCH); + lsm_tree->need_switch = false; ++lsm_tree->dsk_gen; lsm_tree->modified = true; diff --git a/src/lsm/lsm_work_unit.c b/src/lsm/lsm_work_unit.c index dfb8690f1ed..66a57f15875 100644 --- a/src/lsm/lsm_work_unit.c +++ b/src/lsm/lsm_work_unit.c @@ -171,12 +171,12 @@ __wt_lsm_work_switch( *ran = false; *entryp = NULL; - if (F_ISSET(entry->lsm_tree, WT_LSM_TREE_NEED_SWITCH)) { + if (entry->lsm_tree->need_switch) { WT_WITH_SCHEMA_LOCK(session, ret, ret = __wt_lsm_tree_switch(session, entry->lsm_tree)); /* Failing to complete the switch is fine */ if (ret == EBUSY) { - if (F_ISSET(entry->lsm_tree, WT_LSM_TREE_NEED_SWITCH)) + if (entry->lsm_tree->need_switch) WT_ERR(__wt_lsm_manager_push_entry(session, WT_LSM_WORK_SWITCH, 0, entry->lsm_tree)); ret = 0; |