2
0
mirror of https://github.com/boostorg/thread.git synced 2026-02-09 11:32:12 +00:00

Add and fix sleep functions

- Added no_interruption_point::sleep() functions to pthreads to be
  consistent with Windows.
- Fixed an issue where the no_interruption_point::sleep_*() functions
  were still interruptible on Windows.
This commit is contained in:
Austin Beer
2017-10-13 11:37:39 -06:00
parent d70e1aad77
commit 3c01e39481
5 changed files with 200 additions and 184 deletions

View File

@@ -433,10 +433,9 @@ namespace boost
{
namespace hidden
{
void BOOST_THREAD_DECL sleep_for(const detail::platform_duration& ts)
void BOOST_THREAD_DECL sleep_for_internal(const detail::platform_duration& ts)
{
if (ts > detail::platform_duration::zero())
if (ts > detail::platform_duration::zero())
{
// Use pthread_delay_np or nanosleep whenever possible here in the no_interruption_point
// namespace because they do not provide an interruption point.
@@ -449,44 +448,13 @@ namespace boost
# elif defined(BOOST_HAS_NANOSLEEP)
nanosleep(&ts.getTs(), 0);
# else
// Fall back to using a condition variable even though it does provide an interruption point.
const detail::internal_platform_timepoint ts2 = detail::internal_platform_clock::now() + ts;
mutex mx;
unique_lock<mutex> lock(mx);
condition_variable cond;
while (cond.do_wait_until(lock, ts2)) {}
// This should never be reached due to BOOST_THREAD_SLEEP_FOR_IS_STEADY
# endif
}
}
}
}
namespace hidden
{
void BOOST_THREAD_DECL sleep_for(const detail::platform_duration& ts)
{
mutex mx;
unique_lock<mutex> lock(mx);
condition_variable cond;
#if defined(BOOST_THREAD_HAS_MONO_CLOCK) && !defined(BOOST_THREAD_INTERNAL_CLOCK_IS_MONO)
const detail::mono_platform_timepoint& ts2 = detail::mono_platform_clock::now() + ts;
detail::platform_duration d = ts;
while (d > detail::platform_duration::zero())
{
d = (std::min)(d, detail::platform_milliseconds(100));
cond.do_wait_until(lock, detail::internal_platform_clock::now() + d);
d = ts2 - detail::mono_platform_clock::now();
}
#else
const detail::internal_platform_timepoint ts2 = detail::internal_platform_clock::now() + ts;
while (cond.do_wait_until(lock, ts2)) {}
#endif
}
} // hidden
} // this_thread
namespace this_thread
{
void yield() BOOST_NOEXCEPT
{
# if defined(BOOST_HAS_SCHED_YIELD)
@@ -499,7 +467,10 @@ namespace boost
// sleep(xt);
// sleep_for(chrono::milliseconds(0));
# else
hidden::sleep_for(detail::platform_duration::zero());
mutex mx;
unique_lock<mutex> lock(mx);
condition_variable cond;
cond.do_wait_until(lock, detail::internal_platform_clock::now())
# endif
}
}