forked from boostorg/beast
Add some thread classes and fix SharedData with a simple mutex adapter
This commit is contained in:
@@ -78,6 +78,7 @@
|
||||
|
||||
#include "../../beast/CStdInt.h"
|
||||
#include "../../beast/StaticAssert.h"
|
||||
#include "../../beast/Uncopyable.h"
|
||||
|
||||
namespace beast
|
||||
{
|
||||
@@ -94,7 +95,6 @@ extern BEAST_API void BEAST_CALLTYPE logAssertion (char const* file, int line) n
|
||||
// Add new includes to the bottom.
|
||||
|
||||
#include "diagnostic/ContractChecks.h"
|
||||
#include "memory/Uncopyable.h"
|
||||
#include "memory/Memory.h"
|
||||
#include "maths/MathsFunctions.h"
|
||||
#include "memory/ByteOrder.h"
|
||||
@@ -108,6 +108,7 @@ extern BEAST_API void BEAST_CALLTYPE logAssertion (char const* file, int line) n
|
||||
// New header-only library modeled more closely according to boost
|
||||
#include "../../beast/intrusive/ForwardList.h"
|
||||
#include "../../beast/Net.h"
|
||||
#include "../../beast/Thread.h"
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
@@ -161,7 +162,6 @@ namespace beast
|
||||
#include "memory/MemoryAlignment.h"
|
||||
#include "memory/CacheLine.h"
|
||||
#include "threads/ReadWriteMutex.h"
|
||||
#include "threads/SharedData.h"
|
||||
#include "diagnostic/SafeBool.h"
|
||||
#include "threads/WaitableEvent.h"
|
||||
#include "threads/Thread.h"
|
||||
|
||||
@@ -53,7 +53,7 @@ public:
|
||||
|
||||
R operator() ()
|
||||
{
|
||||
return m_f ();
|
||||
return (m_f)();
|
||||
}
|
||||
|
||||
private:
|
||||
@@ -136,7 +136,7 @@ public:
|
||||
|
||||
R operator() (P1 p1)
|
||||
{
|
||||
return m_f (p1);
|
||||
return (m_f)(p1);
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
@@ -262,6 +262,22 @@ private:
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
// bind() helpers for pointer to member function
|
||||
|
||||
template <class T>
|
||||
const T* get_pointer (SharedPtr<T> const& ptr)
|
||||
{
|
||||
return ptr.get();
|
||||
}
|
||||
|
||||
template <class T>
|
||||
T* get_pointer (SharedPtr<T>& ptr)
|
||||
{
|
||||
return ptr.get();
|
||||
}
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
/** SharedPtr comparisons. */
|
||||
/** @{ */
|
||||
template <class T, class U>
|
||||
|
||||
@@ -1,70 +0,0 @@
|
||||
//------------------------------------------------------------------------------
|
||||
/*
|
||||
This file is part of Beast: https://github.com/vinniefalco/Beast
|
||||
Copyright 2013, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
|
||||
Permission to use, copy, modify, and/or distribute this software for any
|
||||
purpose with or without fee is hereby granted, provided that the above
|
||||
copyright notice and this permission notice appear in all copies.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
ANY SPECIAL , DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#ifndef BEAST_UNCOPYABLE_H_INCLUDED
|
||||
#define BEAST_UNCOPYABLE_H_INCLUDED
|
||||
|
||||
/** Prevent copy construction and assignment.
|
||||
|
||||
This is used to suppress warnings and prevent unsafe operations on
|
||||
objects which cannot be passed by value. Ideas based on Boost.
|
||||
|
||||
For example, instead of
|
||||
|
||||
@code
|
||||
|
||||
class MyClass
|
||||
{
|
||||
public:
|
||||
//...
|
||||
|
||||
private:
|
||||
MyClass (const MyClass&);
|
||||
MyClass& operator= (const MyClass&);
|
||||
};
|
||||
|
||||
@endcode
|
||||
|
||||
..you can just write:
|
||||
|
||||
@code
|
||||
|
||||
class MyClass : public Uncopyable
|
||||
{
|
||||
public:
|
||||
//...
|
||||
};
|
||||
|
||||
@endcode
|
||||
|
||||
@note The derivation should be public or else child classes which
|
||||
also derive from Uncopyable may not compile.
|
||||
*/
|
||||
class Uncopyable
|
||||
{
|
||||
protected:
|
||||
inline Uncopyable () { }
|
||||
inline ~Uncopyable () { }
|
||||
|
||||
private:
|
||||
Uncopyable (Uncopyable const&);
|
||||
Uncopyable const& operator= (Uncopyable const&);
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -299,7 +299,7 @@ public:
|
||||
|
||||
void stateChanged ()
|
||||
{
|
||||
SharedData <SharedState>::ReadAccess state (sharedState);
|
||||
SharedData <SharedState>::ConstAccess state (sharedState);
|
||||
|
||||
// (read state)
|
||||
}
|
||||
@@ -308,7 +308,7 @@ public:
|
||||
|
||||
void changeState ()
|
||||
{
|
||||
SharedData <State>::WriteAccess state (sharedState);
|
||||
SharedData <State>::Access state (sharedState);
|
||||
|
||||
// (read and write state)
|
||||
|
||||
|
||||
@@ -137,7 +137,7 @@
|
||||
void addListener (Listener* listener, CallQueue& callQueue)
|
||||
{
|
||||
// Acquire read access to the shared state.
|
||||
SharedData <State>::ReadAccess state (m_state);
|
||||
SharedData <State>::ConstAccess state (m_state);
|
||||
|
||||
// Add the listener.
|
||||
m_listeners.add (listener, callQueue);
|
||||
@@ -171,7 +171,7 @@
|
||||
|
||||
// Update shared state.
|
||||
{
|
||||
SharedData <State>::WriteAccess state (m_state);
|
||||
SharedData <State>::Access state (m_state);
|
||||
|
||||
m_state->outputLevel = newOutputLevel;
|
||||
}
|
||||
|
||||
@@ -205,7 +205,7 @@ bool TrackedMutex::Agent::getLockedList (Array <Record>& output)
|
||||
{
|
||||
TrackedMutex const& mutex = *iter;
|
||||
{
|
||||
TrackedMutex::SharedState::ReadAccess state (mutex.m_state);
|
||||
TrackedMutex::SharedState::ConstAccess state (mutex.m_state);
|
||||
output.add (state->owner);
|
||||
}
|
||||
}
|
||||
@@ -237,7 +237,7 @@ String TrackedMutex::getName () const noexcept
|
||||
TrackedMutex::Record TrackedMutex::getOwnerRecord () const noexcept
|
||||
{
|
||||
{
|
||||
SharedState::ReadAccess state (m_state);
|
||||
SharedState::ConstAccess state (m_state);
|
||||
return state->owner;
|
||||
}
|
||||
}
|
||||
@@ -245,7 +245,7 @@ TrackedMutex::Record TrackedMutex::getOwnerRecord () const noexcept
|
||||
TrackedMutex::Agent TrackedMutex::getOwnerAgent () const noexcept
|
||||
{
|
||||
{
|
||||
SharedState::ReadAccess state (m_state);
|
||||
SharedState::ConstAccess state (m_state);
|
||||
if (state->thread != nullptr)
|
||||
return Agent (state->thread);
|
||||
}
|
||||
@@ -298,7 +298,7 @@ void TrackedMutex::generateGlobalBlockedReport (StringArray& report)
|
||||
{
|
||||
String s;
|
||||
TrackedMutex const& mutex (*iter);
|
||||
TrackedMutex::SharedState::ReadAccess state (mutex.m_state);
|
||||
TrackedMutex::SharedState::ConstAccess state (mutex.m_state);
|
||||
s << " " << mutex.getName () <<
|
||||
" from " << state->owner.getSourceLocation ();
|
||||
report.add (s);
|
||||
@@ -372,7 +372,7 @@ void TrackedMutex::acquired (char const* fileName, int lineNumber) const noexcep
|
||||
|
||||
{
|
||||
// Take a state lock.
|
||||
SharedState::WriteAccess state (m_state);
|
||||
SharedState::Access state (m_state);
|
||||
|
||||
// Set the mutex ownership record
|
||||
state->owner = Record (getName (), threadName, sourceLocation);
|
||||
@@ -428,7 +428,7 @@ void TrackedMutex::release () const noexcept
|
||||
|
||||
{
|
||||
// Take the mutex' state lock
|
||||
SharedState::WriteAccess state (m_state);
|
||||
SharedState::Access state (m_state);
|
||||
|
||||
// Clear the mutex ownership record
|
||||
state->owner = Record ();
|
||||
|
||||
@@ -1,295 +0,0 @@
|
||||
//------------------------------------------------------------------------------
|
||||
/*
|
||||
This file is part of Beast: https://github.com/vinniefalco/Beast
|
||||
Copyright 2013, Vinnie Falco <vinnie.falco@gmail.com>
|
||||
|
||||
Permission to use, copy, modify, and/or distribute this software for any
|
||||
purpose with or without fee is hereby granted, provided that the above
|
||||
copyright notice and this permission notice appear in all copies.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
ANY SPECIAL , DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#ifndef BEAST_SHAREDDATA_H_INCLUDED
|
||||
#define BEAST_SHAREDDATA_H_INCLUDED
|
||||
|
||||
/** Structured access to a shared state.
|
||||
|
||||
This template wraps an object containing members representing state
|
||||
information shared between multiple threads of execution, where any thread
|
||||
may need to read or write as needed. Synchronized access to the concurrent
|
||||
state is enforced at compile time through strongly typed accessor classes.
|
||||
This interface design facilitates source code pattern matching to find all
|
||||
areas where a concurrent state is accessed.
|
||||
|
||||
There are three types of access:
|
||||
|
||||
- ReadAccess
|
||||
|
||||
Allows read access to the underlying object as `const`. ReadAccess may
|
||||
be granted to one or more threads simultaneously. If one or more
|
||||
threads have ReadAccess, requests to obtain WriteAccess are blocked.
|
||||
|
||||
- WriteAccess
|
||||
|
||||
Allows exclusive read/write access the underlying object. A WriteAccess
|
||||
request blocks until all existing ReadAccess and WriteAccess requests
|
||||
are released. While a WriteAccess exists, requests for ReadAccess
|
||||
will block.
|
||||
|
||||
- UnlockedAccess
|
||||
|
||||
Allows read access to the underlying object without using the lock.
|
||||
This can be helpful when designing concurrent structures through
|
||||
composition. It also makes it easier to search for places in code
|
||||
which use unlocked access.
|
||||
|
||||
This code example demonstrates various forms of access to a SharedData:
|
||||
|
||||
@code
|
||||
|
||||
struct SharedData
|
||||
{
|
||||
int value1;
|
||||
String value2;
|
||||
};
|
||||
|
||||
typedef SharedData <SharedData> SharedState;
|
||||
|
||||
SharedState sharedState;
|
||||
|
||||
void readExample ()
|
||||
{
|
||||
SharedState::ReadAccess state (sharedState);
|
||||
|
||||
print (state->value1); // read access
|
||||
print (state->value2); // read access
|
||||
|
||||
state->value1 = 42; // write disallowed: compile error
|
||||
}
|
||||
|
||||
void writeExample ()
|
||||
{
|
||||
SharedState::WriteAccess state (sharedState);
|
||||
|
||||
state->value2 = "Label"; // write access
|
||||
}
|
||||
|
||||
@endcode
|
||||
|
||||
Forwarding constructors with up to eight parameters are provided. This lets
|
||||
you write constructors into the underlying data object. For example:
|
||||
|
||||
@code
|
||||
|
||||
struct SharedData
|
||||
{
|
||||
explicit SharedData (int numSlots)
|
||||
{
|
||||
m_array.reserve (numSlots);
|
||||
}
|
||||
|
||||
std::vector <AudioSampleBuffer*> m_array;
|
||||
};
|
||||
|
||||
// Construct SharedData with one parameter
|
||||
SharedData <SharedData> sharedState (16);
|
||||
|
||||
@endcode
|
||||
|
||||
@param Object The type of object to encapsulate.
|
||||
|
||||
@warning Recursive calls are not supported. It is generally not possible for
|
||||
a thread of execution to acquire write access while it already has
|
||||
read access. Such an attempt will result in undefined behavior.
|
||||
Calling into unknown code while holding a lock can cause deadlock.
|
||||
See @ref CallQueue::queue().
|
||||
*/
|
||||
template <class Object>
|
||||
class SharedData : public Uncopyable
|
||||
{
|
||||
public:
|
||||
class ReadAccess;
|
||||
class WriteAccess;
|
||||
class UnlockedAccess;
|
||||
|
||||
/** Create a concurrent state.
|
||||
|
||||
Up to 8 parameters can be specified in the constructor. These parameters
|
||||
are forwarded to the corresponding constructor in Object. If no
|
||||
constructor in Object matches the parameter list, a compile error is
|
||||
generated.
|
||||
*/
|
||||
/** @{ */
|
||||
SharedData () { }
|
||||
|
||||
template <class T1>
|
||||
explicit SharedData (T1 t1)
|
||||
: m_obj (t1) { }
|
||||
|
||||
template <class T1, class T2>
|
||||
SharedData (T1 t1, T2 t2)
|
||||
: m_obj (t1, t2) { }
|
||||
|
||||
template <class T1, class T2, class T3>
|
||||
SharedData (T1 t1, T2 t2, T3 t3)
|
||||
: m_obj (t1, t2, t3) { }
|
||||
|
||||
template <class T1, class T2, class T3, class T4>
|
||||
SharedData (T1 t1, T2 t2, T3 t3, T4 t4)
|
||||
: m_obj (t1, t2, t3, t4) { }
|
||||
|
||||
template <class T1, class T2, class T3, class T4, class T5>
|
||||
SharedData (T1 t1, T2 t2, T3 t3, T4 t4, T5 t5)
|
||||
: m_obj (t1, t2, t3, t4, t5) { }
|
||||
|
||||
template <class T1, class T2, class T3, class T4, class T5, class T6>
|
||||
SharedData (T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6)
|
||||
: m_obj (t1, t2, t3, t4, t5, t6) { }
|
||||
|
||||
template <class T1, class T2, class T3, class T4, class T5, class T6, class T7>
|
||||
SharedData (T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6, T7 t7) : m_obj (t1, t2, t3, t4, t5, t6, t7) { }
|
||||
|
||||
template <class T1, class T2, class T3, class T4, class T5, class T6, class T7, class T8>
|
||||
SharedData (T1 t1, T2 t2, T3 t3, T4 t4, T5 t5, T6 t6, T7 t7, T8 t8)
|
||||
: m_obj (t1, t2, t3, t4, t5, t6, t7, t8) { }
|
||||
/** @} */
|
||||
|
||||
private:
|
||||
typedef ReadWriteMutex ReadWriteMutexType;
|
||||
|
||||
Object m_obj;
|
||||
ReadWriteMutexType m_mutex;
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
/** Unlocked access to a SharedData.
|
||||
|
||||
Use sparingly.
|
||||
*/
|
||||
template <class Object>
|
||||
class SharedData <Object>::UnlockedAccess : public Uncopyable
|
||||
{
|
||||
public:
|
||||
explicit UnlockedAccess (SharedData const& state)
|
||||
: m_state (state)
|
||||
{
|
||||
}
|
||||
|
||||
Object const& getObject () const
|
||||
{
|
||||
return m_state.m_obj;
|
||||
}
|
||||
Object const& operator* () const
|
||||
{
|
||||
return getObject ();
|
||||
}
|
||||
Object const* operator-> () const
|
||||
{
|
||||
return &getObject ();
|
||||
}
|
||||
|
||||
private:
|
||||
SharedData const& m_state;
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
/** Read only access to a SharedData */
|
||||
template <class Object>
|
||||
class SharedData <Object>::ReadAccess : public Uncopyable
|
||||
{
|
||||
public:
|
||||
/** Create a ReadAccess from the specified SharedData */
|
||||
explicit ReadAccess (SharedData const volatile& state)
|
||||
: m_state (const_cast <SharedData const&> (state))
|
||||
, m_lock (m_state.m_mutex)
|
||||
{
|
||||
}
|
||||
|
||||
/** Obtain a read only reference to Object */
|
||||
Object const& getObject () const
|
||||
{
|
||||
return m_state.m_obj;
|
||||
}
|
||||
|
||||
/** Obtain a read only reference to Object */
|
||||
Object const& operator* () const
|
||||
{
|
||||
return getObject ();
|
||||
}
|
||||
|
||||
/** Obtain a read only smart pointer to Object */
|
||||
Object const* operator-> () const
|
||||
{
|
||||
return &getObject ();
|
||||
}
|
||||
|
||||
private:
|
||||
SharedData const& m_state;
|
||||
ReadWriteMutexType::ScopedReadLockType m_lock;
|
||||
};
|
||||
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
/** Read/write access to a SharedData */
|
||||
template <class Object>
|
||||
class SharedData <Object>::WriteAccess : public Uncopyable
|
||||
{
|
||||
public:
|
||||
explicit WriteAccess (SharedData& state)
|
||||
: m_state (state)
|
||||
, m_lock (m_state.m_mutex)
|
||||
{
|
||||
}
|
||||
|
||||
/** Obtain a read only reference to Object */
|
||||
Object const* getObject () const
|
||||
{
|
||||
return m_state.m_obj;
|
||||
}
|
||||
|
||||
/** Obtain a read only reference to Object */
|
||||
Object const& operator* () const
|
||||
{
|
||||
return getObject ();
|
||||
}
|
||||
|
||||
/** Obtain a read only smart pointer to Object */
|
||||
Object const* operator-> () const
|
||||
{
|
||||
return &getObject ();
|
||||
}
|
||||
|
||||
/** Obtain a read/write pointer to Object */
|
||||
Object& getObject ()
|
||||
{
|
||||
return m_state.m_obj;
|
||||
}
|
||||
|
||||
/** Obtain a read/write reference to Object */
|
||||
Object& operator* ()
|
||||
{
|
||||
return getObject ();
|
||||
}
|
||||
|
||||
/** Obtain a read/write smart pointer to Object */
|
||||
Object* operator-> ()
|
||||
{
|
||||
return &getObject ();
|
||||
}
|
||||
|
||||
private:
|
||||
SharedData& m_state;
|
||||
ReadWriteMutexType::ScopedWriteLockType m_lock;
|
||||
};
|
||||
|
||||
#endif
|
||||
@@ -21,8 +21,8 @@
|
||||
*/
|
||||
//==============================================================================
|
||||
|
||||
#ifndef BEAST_THREAD_H_INCLUDED
|
||||
#define BEAST_THREAD_H_INCLUDED
|
||||
#ifndef BEAST_JUCE_THREAD_H_INCLUDED
|
||||
#define BEAST_JUCE_THREAD_H_INCLUDED
|
||||
|
||||
//==============================================================================
|
||||
/**
|
||||
|
||||
@@ -255,7 +255,7 @@ public:
|
||||
, m_keyBlockDepth (keyBlockDepth)
|
||||
, m_keyStorage (keyBytes)
|
||||
{
|
||||
SharedState::WriteAccess state (m_state);
|
||||
SharedState::Access state (m_state);
|
||||
|
||||
openFile (&state->keyFile, keyPath);
|
||||
|
||||
@@ -289,7 +289,7 @@ public:
|
||||
|
||||
~KeyvaDBImp ()
|
||||
{
|
||||
SharedState::WriteAccess state (m_state);
|
||||
SharedState::Access state (m_state);
|
||||
|
||||
flushInternal (state);
|
||||
}
|
||||
@@ -310,7 +310,7 @@ public:
|
||||
|
||||
//--------------------------------------------------------------------------
|
||||
|
||||
Result createMasterRecord (SharedState::WriteAccess& state)
|
||||
Result createMasterRecord (SharedState::Access& state)
|
||||
{
|
||||
MemoryBlock buffer (masterHeaderBytes, true);
|
||||
|
||||
@@ -344,7 +344,7 @@ public:
|
||||
//
|
||||
void readKeyRecord (KeyRecord* const keyRecord,
|
||||
KeyIndex const keyIndex,
|
||||
SharedState::WriteAccess& state)
|
||||
SharedState::Access& state)
|
||||
{
|
||||
FileOffset const byteOffset = calcKeyRecordOffset (keyIndex);
|
||||
|
||||
@@ -391,7 +391,7 @@ public:
|
||||
// Write a key record from memory
|
||||
void writeKeyRecord (KeyRecord const& keyRecord,
|
||||
KeyIndex const keyIndex,
|
||||
SharedState::WriteAccess& state,
|
||||
SharedState::Access& state,
|
||||
bool includingKey)
|
||||
{
|
||||
FileOffset const byteOffset = calcKeyRecordOffset (keyIndex);
|
||||
@@ -442,7 +442,7 @@ public:
|
||||
|
||||
// Append a value to the value file.
|
||||
// VFALCO TODO return a Result
|
||||
void writeValue (void const* const value, ByteSize valueBytes, SharedState::WriteAccess& state)
|
||||
void writeValue (void const* const value, ByteSize valueBytes, SharedState::Access& state)
|
||||
{
|
||||
Result result = state->valFile.setPosition (state->valFileSize);
|
||||
|
||||
@@ -493,7 +493,7 @@ public:
|
||||
//
|
||||
// Returns true if the key was found.
|
||||
//
|
||||
bool find (FindResult* findResult, void const* key, SharedState::WriteAccess& state)
|
||||
bool find (FindResult* findResult, void const* key, SharedState::Access& state)
|
||||
{
|
||||
// Not okay to call this with an empty key file!
|
||||
bassert (state->hasKeys ());
|
||||
@@ -546,7 +546,7 @@ public:
|
||||
{
|
||||
FindResult findResult (m_keyStorage.getData ());
|
||||
|
||||
SharedState::WriteAccess state (m_state);
|
||||
SharedState::Access state (m_state);
|
||||
|
||||
bool found = false;
|
||||
|
||||
@@ -594,7 +594,7 @@ public:
|
||||
{
|
||||
bassert (valueBytes > 0);
|
||||
|
||||
SharedState::WriteAccess state (m_state);
|
||||
SharedState::Access state (m_state);
|
||||
|
||||
if (state->hasKeys ())
|
||||
{
|
||||
@@ -681,12 +681,12 @@ public:
|
||||
|
||||
void flush ()
|
||||
{
|
||||
SharedState::WriteAccess state (m_state);
|
||||
SharedState::Access state (m_state);
|
||||
|
||||
flushInternal (state);
|
||||
}
|
||||
|
||||
void flushInternal (SharedState::WriteAccess& state)
|
||||
void flushInternal (SharedState::Access& state)
|
||||
{
|
||||
state->keyFile.flush ();
|
||||
state->valFile.flush ();
|
||||
|
||||
Reference in New Issue
Block a user