diff options
author | Jonathan Wakely <jwakely@redhat.com> | 2017-03-05 18:38:35 +0000 |
---|---|---|
committer | Jonathan Wakely <redi@gcc.gnu.org> | 2017-03-05 18:38:35 +0000 |
commit | f620e1d5c84586f6e60bf5350946ea4a75154ff4 (patch) | |
tree | a3d7288f3ed77f2935a5140ef1f8c0f45a0d5539 /libstdc++-v3/include/std/mutex | |
parent | d8b4baeb45c2727156e6d14e1dee16e078c0a727 (diff) | |
download | gcc-f620e1d5c84586f6e60bf5350946ea4a75154ff4.tar.gz |
Add std::scoped_lock for C++17
* doc/xml/manual/status_cxx2017.xml: Document P0156R2 status.
* doc/html/*: Regenerate.
* include/std/mutex (scoped_lock): Implement new C++17 template.
* testsuite/30_threads/scoped_lock/cons/1.cc: New test.
* testsuite/30_threads/scoped_lock/requirements/
explicit_instantiation.cc: New test.
* testsuite/30_threads/scoped_lock/requirements/typedefs.cc: New test.
From-SVN: r245903
Diffstat (limited to 'libstdc++-v3/include/std/mutex')
-rw-r--r-- | libstdc++-v3/include/std/mutex | 68 |
1 files changed, 68 insertions, 0 deletions
diff --git a/libstdc++-v3/include/std/mutex b/libstdc++-v3/include/std/mutex index d6f3899e4f6..6c3f92022be 100644 --- a/libstdc++-v3/include/std/mutex +++ b/libstdc++-v3/include/std/mutex @@ -556,6 +556,74 @@ _GLIBCXX_BEGIN_NAMESPACE_VERSION } } +#if __cplusplus > 201402L +#define __cpp_lib_scoped_lock 201703 + /** @brief A scoped lock type for multiple lockable objects. + * + * A scoped_lock controls mutex ownership within a scope, releasing + * ownership in the destructor. + */ + template<typename... _MutexTypes> + class scoped_lock + { + public: + explicit scoped_lock(_MutexTypes&... __m) : _M_devices(std::tie(__m...)) + { std::lock(__m...); } + + explicit scoped_lock(_MutexTypes&... __m, adopt_lock_t) noexcept + : _M_devices(std::tie(__m...)) + { } // calling thread owns mutex + + ~scoped_lock() + { + std::apply([](_MutexTypes&... __m) { + char __i[] __attribute__((__unused__)) = { (__m.unlock(), 0)... }; + }, _M_devices); + } + + scoped_lock(const scoped_lock&) = delete; + scoped_lock& operator=(const scoped_lock&) = delete; + + private: + tuple<_MutexTypes&...> _M_devices; + }; + + template<> + class scoped_lock<> + { + public: + explicit scoped_lock() = default; + explicit scoped_lock(adopt_lock_t) noexcept { } + ~scoped_lock() = default; + + scoped_lock(const scoped_lock&) = delete; + scoped_lock& operator=(const scoped_lock&) = delete; + }; + + template<typename _Mutex> + class scoped_lock<_Mutex> + { + public: + using mutex_type = _Mutex; + + explicit scoped_lock(mutex_type& __m) : _M_device(__m) + { _M_device.lock(); } + + explicit scoped_lock(mutex_type& __m, adopt_lock_t) noexcept + : _M_device(__m) + { } // calling thread owns mutex + + ~scoped_lock() + { _M_device.unlock(); } + + scoped_lock(const scoped_lock&) = delete; + scoped_lock& operator=(const scoped_lock&) = delete; + + private: + mutex_type& _M_device; + }; +#endif // C++17 + #ifdef _GLIBCXX_HAS_GTHREADS /// once_flag struct once_flag |