Audacity 3.2.0
ClientDataHelpers.h
Go to the documentation of this file.
1/*!********************************************************************
2
3Audacity: A Digital Audio Editor
4
5@file ClientDataHelpers.h
6@brief Some implementation details for ClientData
7
8Paul Licameli
9
10**********************************************************************/
11
12#ifndef __AUDACITY_CLIENT_DATA_HELPERS__
13#define __AUDACITY_CLIENT_DATA_HELPERS__
14
15#include <memory>
16#include <mutex>
17#include <type_traits>
18
19namespace ClientData {
20 // Helpers to define ClientData::Site class template
21
23
28};
29
31
37};
38
39// forward declarations
40struct Base;
41template<
42 typename Covariant,
43 template<typename> class Owner
44> struct Cloneable;
45
47
48template< typename Ptr > static inline
49 const Ptr &Dereferenceable( Ptr &p )
50 { return p; }
52template< typename Obj > static inline
53 std::shared_ptr<Obj> Dereferenceable( std::weak_ptr<Obj> &p )
54 { return p.lock(); }
55
57
61template< typename Object, LockingPolicy > struct Lockable{};
63template< typename Object > struct Lockable< Object, NoLocking >
64: Object {
66 struct Lock{};
67 Lock lock() const { return {}; }
68};
70template< typename Object > struct Lockable< Object, NonrecursiveLocking >
71: Object, std::mutex {
72 using Lock = std::unique_lock< std::mutex >;
73 Lock lock() const { return Lock{ *this }; }
74};
76template< typename Object > struct Lockable< Object, RecursiveLocking >
77: Object, std::recursive_mutex {
78 using Lock = std::unique_lock< std::recursive_mutex >;
79 Lock lock() const { return Lock{ *this }; }
80};
81
83
84template< typename Lockable > struct Locked
85 : private Lockable::Lock
86{
87 explicit Locked( Lockable &object )
88 : Lockable::Lock( object.lock() )
89 , mObject( object )
90 {}
92};
93
95template< typename Container, CopyingPolicy > struct Copyable{};
97template< typename Container > struct Copyable< Container, SkipCopying >
98: Container {
99 Copyable() = default;
100 Copyable( const Copyable & ) {}
101 Copyable &operator=( const Copyable & ) { return *this; }
102 Copyable( Copyable && ) = default;
103 Copyable &operator=( Copyable&& ) = default;
104};
106template< typename Container > struct Copyable< Container, ShallowCopying >
107: Container {
108 Copyable() = default;
110 Copyable( const Copyable &other )
111 { *this = other; }
113 Copyable &operator=( const Copyable &other )
114 {
115 if (this != &other) {
116 // Build then swap for strong exception guarantee
117 Copyable temp;
118 for ( auto &&ptr : other )
119 temp.push_back( ptr );
120 this->swap( temp );
121 }
122 return *this;
123 }
124 Copyable( Copyable && ) = default;
125 Copyable &operator=( Copyable&& ) = default;
126};
128template< typename Container > struct Copyable< Container, DeepCopying >
129: Container {
130 Copyable() = default;
132 Copyable( const Copyable &other )
133 { *this = other; }
135 Copyable &operator=( const Copyable &other )
136 {
137 if (this != &other) {
138 // Build then swap for strong exception guarantee
139 Copyable temp;
140 for ( auto &&p : other ) {
141 using Ptr = decltype( p->Clone() );
142 temp.push_back( p ? p->Clone() : Ptr{} );
143 }
144 this->swap( temp );
145 }
146 return *this;
147 }
148 Copyable( Copyable && ) = default;
149 Copyable &operator=( Copyable&& ) = default;
150};
151
152}
153
154#endif
Utility ClientData::Site to register hooks into a host class that attach client data.
Definition: ClientData.h:25
static const Ptr & Dereferenceable(Ptr &p)
Conversion allowing operator * on any Pointer parameter of ClientData::Site.
CopyingPolicy
Statically specify how the ClientData::Site implements its copy constructor and assignment.
@ ShallowCopying
copy pointers only; won't compile for std::unique_ptr
@ SkipCopying
ignore the source and leave empty
@ DeepCopying
point to new sub-objects; these must define a Clone() member; won't compile for std::weak_ptr
LockingPolicy
Statically specify whether there is mutual exclusion (separately for the table of factories,...
@ RecursiveLocking
using std::recursive_mutex
@ NonrecursiveLocking
using std::mutex
void swap(std::unique_ptr< Alg_seq > &a, std::unique_ptr< Alg_seq > &b)
Definition: NoteTrack.cpp:634
Copyable & operator=(Copyable &&)=default
Copyable & operator=(const Copyable &other)
Copyable(const Copyable &other)
Call through to operator =.
Copyable(const Copyable &other)
Call through to operator =.
Copyable & operator=(Copyable &&)=default
Copyable & operator=(Copyable &&)=default
Decorator template injects copy and move operators for container of pointers.
std::unique_lock< std::recursive_mutex > Lock
Decorator template injects type Lock and method lock() into interface of Object.
Decorated reference to a ClientData::Lockable, with a current lock on it.
Locked(Lockable &object)