From 0af027db5a233d835d2ac3e2e98461bb674f169c Mon Sep 17 00:00:00 2001 From: Matthew V Date: Thu, 13 Mar 2014 14:27:46 -0400 Subject: [PATCH] correct prefetch race condition. --- c_src/eleveldb.cc | 12 +++++++++--- test/eleveldb_schema_tests.erl | 2 +- 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/c_src/eleveldb.cc b/c_src/eleveldb.cc index d322547a..bf9d2545 100644 --- a/c_src/eleveldb.cc +++ b/c_src/eleveldb.cc @@ -2,7 +2,7 @@ // // eleveldb: Erlang Wrapper for LevelDB (http://code.google.com/p/leveldb/) // -// Copyright (c) 2011-2013 Basho Technologies, Inc. All Rights Reserved. +// Copyright (c) 2011-2014 Basho Technologies, Inc. All Rights Reserved. // // This file is provided to you under the Apache License, // Version 2.0 (the "License"); you may not use this file @@ -738,7 +738,7 @@ async_iterator_move( const ERL_NIF_TERM& action_or_target = argv[2]; ERL_NIF_TERM ret_term; - bool submit_new_request(true); + bool submit_new_request(true), prefetch_state; ReferencePtr itr_ptr; @@ -768,6 +768,11 @@ async_iterator_move( // debug syslog(LOG_ERR, "move state: %d, %d, %d", // action, itr_ptr->m_Iter->m_PrefetchStarted, itr_ptr->m_Iter->m_HandoffAtomic); + // must set this BEFORE call to compare_and_swap ... or have potential + // for an "extra" message coming out of prefetch + prefetch_state = itr_ptr->m_Iter->m_PrefetchStarted; + itr_ptr->m_Iter->m_PrefetchStarted = prefetch_state && (eleveldb::MoveTask::PREFETCH_STOP != action ); + // // Three situations: // #1 not a PREFETCH next call @@ -802,7 +807,7 @@ async_iterator_move( // leave m_HandoffAtomic as 1 so first response is via message // is this truly a wait for prefetch ... or actually the first prefetch request - if (!itr_ptr->m_Iter->m_PrefetchStarted) + if (!prefetch_state) { submit_new_request=true; itr_ptr->ReleaseReuseMove(); @@ -814,6 +819,7 @@ async_iterator_move( submit_new_request=false; } // else + // redundant ... but clarifying where it really belongs in logic pattern itr_ptr->m_Iter->m_PrefetchStarted=(eleveldb::MoveTask::PREFETCH_STOP != action ); } // else if diff --git a/test/eleveldb_schema_tests.erl b/test/eleveldb_schema_tests.erl index 9c95a102..76c5d501 100644 --- a/test/eleveldb_schema_tests.erl +++ b/test/eleveldb_schema_tests.erl @@ -13,7 +13,7 @@ basic_schema_test() -> ["../priv/eleveldb.schema"], [], context(), predefined_schema()), cuttlefish_unit:assert_config(Config, "eleveldb.data_root", "./data/leveldb"), - cuttlefish_unit:assert_config(Config, "eleveldb.total_leveldb_mem_percent", 80), + cuttlefish_unit:assert_config(Config, "eleveldb.total_leveldb_mem_percent", 70), cuttlefish_unit:assert_not_configured(Config, "eleveldb.total_leveldb_mem"), cuttlefish_unit:assert_config(Config, "eleveldb.sync", false), cuttlefish_unit:assert_config(Config, "eleveldb.limited_developer_mem", false),