summaryrefslogtreecommitdiff
path: root/sal
diff options
context:
space:
mode:
authorNoel Grandin <noel.grandin@collabora.co.uk>2023-02-14 10:48:56 +0200
committerNoel Grandin <noel.grandin@collabora.co.uk>2023-02-16 09:00:51 +0000
commit65efe0e2783660780da7dc126e5f34422f312814 (patch)
tree1e74c1b61af4a992706a12b284d8b3cf8275d7e8 /sal
parentb96a0a214ba98701ff56a0b531d652c6905d6c1e (diff)
use std::condition_variable for oslCondition
which is both faster (because we don't need to allocate a pthread condition) and simpler Change-Id: I0a98432b5106c1c2b8e8ed97cbd779ef2b0c9e4d Reviewed-on: https://gerrit.libreoffice.org/c/core/+/146996 Tested-by: Jenkins Reviewed-by: Noel Grandin <noel.grandin@collabora.co.uk>
Diffstat (limited to 'sal')
-rw-r--r--sal/osl/unx/conditn.cxx169
1 files changed, 25 insertions, 144 deletions
diff --git a/sal/osl/unx/conditn.cxx b/sal/osl/unx/conditn.cxx
index 602240922b8c..16c4ad11b15f 100644
--- a/sal/osl/unx/conditn.cxx
+++ b/sal/osl/unx/conditn.cxx
@@ -20,9 +20,9 @@
#include <sal/config.h>
#include <assert.h>
+#include <condition_variable>
+#include <mutex>
-#include "system.hxx"
-#include "unixerrnostring.hxx"
#include <sal/log.hxx>
#include <sal/types.h>
@@ -33,48 +33,16 @@ namespace {
struct oslConditionImpl
{
- pthread_cond_t m_Condition;
- pthread_mutex_t m_Lock;
- bool m_State;
+ std::condition_variable m_Condition;
+ std::mutex m_Lock;
+ bool m_State = false;
};
}
oslCondition SAL_CALL osl_createCondition()
{
- oslConditionImpl* pCond;
- int nRet=0;
-
- pCond = static_cast<oslConditionImpl*>(malloc(sizeof(oslConditionImpl)));
-
- if ( pCond == nullptr )
- {
- return nullptr;
- }
-
- pCond->m_State = false;
-
- /* init condition variable with default attr. (PTHREAD_PROCESS_PRIVAT) */
- nRet = pthread_cond_init(&pCond->m_Condition, PTHREAD_CONDATTR_DEFAULT);
- if ( nRet != 0 )
- {
- SAL_WARN( "sal.osl.condition", "pthread_cond_init failed: " << UnixErrnoString(nRet) );
-
- free(pCond);
- return nullptr;
- }
-
- nRet = pthread_mutex_init(&pCond->m_Lock, PTHREAD_MUTEXATTR_DEFAULT);
- if ( nRet != 0 )
- {
- SAL_WARN( "sal.osl.condition", "pthread_mutex_init failed: " << UnixErrnoString(nRet) );
-
- nRet = pthread_cond_destroy(&pCond->m_Condition);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "pthread_cond_destroy failed: " << UnixErrnoString(nRet) );
-
- free(pCond);
- pCond = nullptr;
- }
+ oslConditionImpl* pCond = new oslConditionImpl;
SAL_INFO( "sal.osl.condition", "osl_createCondition(): " << pCond );
@@ -90,48 +58,22 @@ void SAL_CALL osl_destroyCondition(oslCondition Condition)
SAL_INFO( "sal.osl.condition", "osl_destroyCondition(" << pCond << ")" );
if ( pCond )
- {
- int nRet = pthread_cond_destroy(&pCond->m_Condition);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "pthread_cond_destroy failed: " << UnixErrnoString(nRet) );
- nRet = pthread_mutex_destroy(&pCond->m_Lock);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "pthread_mutex_destroy failed: " << UnixErrnoString(nRet) );
-
- free(Condition);
- }
+ delete pCond;
}
sal_Bool SAL_CALL osl_setCondition(oslCondition Condition)
{
oslConditionImpl* pCond;
- int nRet=0;
assert(Condition);
pCond = static_cast<oslConditionImpl*>(Condition);
- nRet = pthread_mutex_lock(&pCond->m_Lock);
- if ( nRet != 0 )
{
- SAL_WARN( "sal.osl.condition", "osl_setCondition(" << pCond << "): pthread_mutex_lock failed: " << UnixErrnoString(nRet) );
- return false;
- }
-
- pCond->m_State = true;
- nRet = pthread_cond_broadcast(&pCond->m_Condition);
- if ( nRet != 0 )
- {
- SAL_WARN( "sal.osl.condition", "osl_setCondition(" << pCond << "): pthread_cond_broadcast failed: " << UnixErrnoString(nRet) );
- // try to unlock the mutex
- pthread_mutex_unlock(&pCond->m_Lock);
- return false;
- }
+ std::unique_lock g(pCond->m_Lock);
- nRet = pthread_mutex_unlock(&pCond->m_Lock);
- if ( nRet != 0 )
- {
- SAL_WARN( "sal.osl.condition", "osl_setCondition(" << pCond << "): pthread_mutex_unlock failed: " << UnixErrnoString(nRet) );
- return false;
+ pCond->m_State = true;
+ pCond->m_Condition.notify_all();
}
-
SAL_INFO( "sal.osl.condition", "osl_setCondition(" << pCond << ")" );
return true;
@@ -141,28 +83,16 @@ sal_Bool SAL_CALL osl_setCondition(oslCondition Condition)
sal_Bool SAL_CALL osl_resetCondition(oslCondition Condition)
{
oslConditionImpl* pCond;
- int nRet=0;
assert(Condition);
pCond = static_cast<oslConditionImpl*>(Condition);
- nRet = pthread_mutex_lock(&pCond->m_Lock);
- if ( nRet != 0 )
{
- SAL_WARN( "sal.osl.condition", "osl_resetCondition(" << pCond << "): pthread_mutex_lock failed: " << UnixErrnoString(nRet) );
- return false;
- }
+ std::unique_lock g(pCond->m_Lock);
- pCond->m_State = false;
-
- nRet = pthread_mutex_unlock(&pCond->m_Lock);
- if ( nRet != 0 )
- {
- SAL_WARN( "sal.osl.condition", "osl_resetCondition(" << pCond << "): pthread_mutex_unlock failed: " << UnixErrnoString(nRet) );
- return false;
+ pCond->m_State = false;
}
-
SAL_INFO( "sal.osl.condition", "osl_resetCondition(" << pCond << ")" );
return true;
@@ -171,75 +101,30 @@ sal_Bool SAL_CALL osl_resetCondition(oslCondition Condition)
oslConditionResult SAL_CALL osl_waitCondition(oslCondition Condition, const TimeValue* pTimeout)
{
oslConditionImpl* pCond;
- int nRet=0;
assert(Condition);
pCond = static_cast<oslConditionImpl*>(Condition);
SAL_INFO( "sal.osl.condition", "osl_waitCondition(" << pCond << ")" );
- nRet = pthread_mutex_lock(&pCond->m_Lock);
- if ( nRet != 0 )
{
- SAL_WARN( "sal.osl.condition", "osl_waitCondition(" << pCond << "): pthread_mutex_lock failed: " << UnixErrnoString(nRet) );
- return osl_cond_result_error;
- }
+ std::unique_lock g(pCond->m_Lock);
- if ( pTimeout )
- {
- if ( ! pCond->m_State )
+ if ( pTimeout )
{
- struct timeval tp;
- struct timespec to;
-
- gettimeofday(&tp, nullptr);
-
- SET_TIMESPEC( to, tp.tv_sec + pTimeout->Seconds,
- tp.tv_usec * 1000 + pTimeout->Nanosec );
-
- /* spurious wake up prevention */
- do
+ if ( ! pCond->m_State )
{
- const int ret = pthread_cond_timedwait(&pCond->m_Condition, &pCond->m_Lock, &to);
- if ( ret != 0 )
- {
- if ( ret == ETIME || ret == ETIMEDOUT )
- {
- nRet = pthread_mutex_unlock(&pCond->m_Lock);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "osl_waitCondition(" << pCond << "): pthread_mutex_unlock failed: " << UnixErrnoString(nRet) );
-
- return osl_cond_result_timeout;
- }
- if ( ret != EINTR )
- {
- nRet = pthread_mutex_unlock(&pCond->m_Lock);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "osl_waitCondition(" << pCond << "): pthread_mutex_unlock failed: " << UnixErrnoString(nRet) );
- return osl_cond_result_error;
- }
- }
+ auto duration = std::chrono::seconds(pTimeout->Seconds)
+ + std::chrono::nanoseconds(pTimeout->Nanosec);
+ if (!pCond->m_Condition.wait_for(g, duration, [&pCond](){return pCond->m_State;}))
+ return osl_cond_result_timeout;
}
- while ( !pCond->m_State );
}
- }
- else
- {
- while ( !pCond->m_State )
+ else
{
- nRet = pthread_cond_wait(&pCond->m_Condition, &pCond->m_Lock);
- if ( nRet != 0 )
- {
- SAL_WARN( "sal.osl.condition", "osl_waitCondition(" << pCond << "): pthread_cond_wait failed: " << UnixErrnoString(nRet) );
- nRet = pthread_mutex_unlock(&pCond->m_Lock);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "osl_waitCondition(" << pCond << "): pthread_mutex_unlock failed: " << UnixErrnoString(nRet) );
-
- return osl_cond_result_error;
- }
+ pCond->m_Condition.wait(g, [&pCond](){return pCond->m_State;});
}
}
-
- nRet = pthread_mutex_unlock(&pCond->m_Lock);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "osl_waitCondition(" << pCond << "): pthread_mutex_unlock failed: " << UnixErrnoString(nRet) );
-
SAL_INFO( "sal.osl.condition", "osl_waitCondition(" << pCond << "): OK" );
return osl_cond_result_ok;
@@ -249,19 +134,15 @@ sal_Bool SAL_CALL osl_checkCondition(oslCondition Condition)
{
bool State;
oslConditionImpl* pCond;
- int nRet=0;
assert(Condition);
pCond = static_cast<oslConditionImpl*>(Condition);
- nRet = pthread_mutex_lock(&pCond->m_Lock);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "osl_checkCondition(" << pCond << "): pthread_mutex_lock failed: " << UnixErrnoString(nRet) );
-
- State = pCond->m_State;
-
- nRet = pthread_mutex_unlock(&pCond->m_Lock);
- SAL_WARN_IF( nRet != 0, "sal.osl.condition", "osl_checkCondition(" << pCond << "): pthread_mutex_unlock failed: " << UnixErrnoString(nRet) );
+ {
+ std::unique_lock g(pCond->m_Lock);
+ State = pCond->m_State;
+ }
SAL_INFO( "sal.osl.condition", "osl_checkCondition(" << pCond << "): " << (State ? "YES" : "NO") );
return State;