What is often done is to create internal APIs that do not take locks that are called by the public APIs that do take the locks.
void Logger::error( string msg )
{
wxCRIT_SECT_LOCKER(adapter_locker, gs_LogBufferShield);
m_err_cnt++;
do_log_internal("Error: " + msg);
}
void Logger::warning( string msg )
{
wxCRIT_SECT_LOCKER(adapter_locker, gs_LogBufferShield);
m_warn_cnt++;
do_log_internal("Warning: " + msg);
}
void Logger::do_log( string msg )
{
wxCRIT_SECT_LOCKER(adapter_locker, gs_LogBufferShield);
do_log_internal(msg);
}
void Logger::do_log_internal( string msg )
{
m_log_cnt++;
cout << msg << endl;
}
However, for your problem, you may rather use wxMutex
directly, and use the type wxMUTEX_RECURSIVE
when you construct it. This way, a mutex has count. When the mutex is first locked, the count is set to 1. If the same thread grabs the mutex again, it increments a count. Releasing the mutex decrements the count. When the count reaches 0, the mutex is unlocked.