summaryrefslogtreecommitdiff
path: root/include/mutex
diff options
context:
space:
mode:
authorDimitry Andric <dim@FreeBSD.org>2015-09-06 18:46:46 +0000
committerDimitry Andric <dim@FreeBSD.org>2015-09-06 18:46:46 +0000
commit61b9a7258a7693d7f3674a5a1daf7b036ff1d382 (patch)
treeec41ed70ffca97240e76f9a78bb2dedba28f310c /include/mutex
parentf857581820d15e410e9945d2fcd5f7163be25a96 (diff)
downloadsrc-test2-61b9a7258a7693d7f3674a5a1daf7b036ff1d382.tar.gz
src-test2-61b9a7258a7693d7f3674a5a1daf7b036ff1d382.zip
Notes
Diffstat (limited to 'include/mutex')
-rw-r--r--include/mutex57
1 files changed, 34 insertions, 23 deletions
diff --git a/include/mutex b/include/mutex
index e2a0daa3eab5..373d75b09789 100644
--- a/include/mutex
+++ b/include/mutex
@@ -175,6 +175,7 @@ template<class Callable, class ...Args>
#include <__config>
#include <__mutex_base>
#include <functional>
+#include <memory>
#ifndef _LIBCPP_HAS_NO_VARIADICS
#include <tuple>
#endif
@@ -442,7 +443,11 @@ void call_once(once_flag&, _Callable&&, _Args&&...);
template<class _Callable>
_LIBCPP_INLINE_VISIBILITY
-void call_once(once_flag&, _Callable);
+void call_once(once_flag&, _Callable&);
+
+template<class _Callable>
+_LIBCPP_INLINE_VISIBILITY
+void call_once(once_flag&, const _Callable&);
#endif // _LIBCPP_HAS_NO_VARIADICS
@@ -465,7 +470,11 @@ private:
#else // _LIBCPP_HAS_NO_VARIADICS
template<class _Callable>
friend
- void call_once(once_flag&, _Callable);
+ void call_once(once_flag&, _Callable&);
+
+ template<class _Callable>
+ friend
+ void call_once(once_flag&, const _Callable&);
#endif // _LIBCPP_HAS_NO_VARIADICS
};
@@ -474,15 +483,10 @@ private:
template <class _Fp>
class __call_once_param
{
- _Fp __f_;
+ _Fp& __f_;
public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
_LIBCPP_INLINE_VISIBILITY
- explicit __call_once_param(_Fp&& __f) : __f_(_VSTD::move(__f)) {}
-#else
- _LIBCPP_INLINE_VISIBILITY
- explicit __call_once_param(const _Fp& __f) : __f_(__f) {}
-#endif
+ explicit __call_once_param(_Fp& __f) : __f_(__f) {}
_LIBCPP_INLINE_VISIBILITY
void operator()()
@@ -496,7 +500,7 @@ private:
_LIBCPP_INLINE_VISIBILITY
void __execute(__tuple_indices<_Indices...>)
{
- __invoke(_VSTD::move(_VSTD::get<0>(__f_)), _VSTD::move(_VSTD::get<_Indices>(__f_))...);
+ __invoke(_VSTD::get<0>(_VSTD::move(__f_)), _VSTD::get<_Indices>(_VSTD::move(__f_))...);
}
};
@@ -505,15 +509,10 @@ private:
template <class _Fp>
class __call_once_param
{
- _Fp __f_;
+ _Fp& __f_;
public:
-#ifndef _LIBCPP_HAS_NO_RVALUE_REFERENCES
_LIBCPP_INLINE_VISIBILITY
- explicit __call_once_param(_Fp&& __f) : __f_(_VSTD::move(__f)) {}
-#else
- _LIBCPP_INLINE_VISIBILITY
- explicit __call_once_param(const _Fp& __f) : __f_(__f) {}
-#endif
+ explicit __call_once_param(_Fp& __f) : __f_(__f) {}
_LIBCPP_INLINE_VISIBILITY
void operator()()
@@ -541,11 +540,11 @@ inline _LIBCPP_INLINE_VISIBILITY
void
call_once(once_flag& __flag, _Callable&& __func, _Args&&... __args)
{
- if (__flag.__state_ != ~0ul)
+ if (__libcpp_relaxed_load(&__flag.__state_) != ~0ul)
{
- typedef tuple<typename decay<_Callable>::type, typename decay<_Args>::type...> _Gp;
- __call_once_param<_Gp> __p(_Gp(__decay_copy(_VSTD::forward<_Callable>(__func)),
- __decay_copy(_VSTD::forward<_Args>(__args))...));
+ typedef tuple<_Callable&&, _Args&&...> _Gp;
+ _Gp __f(_VSTD::forward<_Callable>(__func), _VSTD::forward<_Args>(__args)...);
+ __call_once_param<_Gp> __p(__f);
__call_once(__flag.__state_, &__p, &__call_once_proxy<_Gp>);
}
}
@@ -555,15 +554,27 @@ call_once(once_flag& __flag, _Callable&& __func, _Args&&... __args)
template<class _Callable>
inline _LIBCPP_INLINE_VISIBILITY
void
-call_once(once_flag& __flag, _Callable __func)
+call_once(once_flag& __flag, _Callable& __func)
{
- if (__flag.__state_ != ~0ul)
+ if (__libcpp_relaxed_load(&__flag.__state_) != ~0ul)
{
__call_once_param<_Callable> __p(__func);
__call_once(__flag.__state_, &__p, &__call_once_proxy<_Callable>);
}
}
+template<class _Callable>
+inline _LIBCPP_INLINE_VISIBILITY
+void
+call_once(once_flag& __flag, const _Callable& __func)
+{
+ if (__flag.__state_ != ~0ul)
+ {
+ __call_once_param<const _Callable> __p(__func);
+ __call_once(__flag.__state_, &__p, &__call_once_proxy<const _Callable>);
+ }
+}
+
#endif // _LIBCPP_HAS_NO_VARIADICS
_LIBCPP_END_NAMESPACE_STD