ALib C++ Library
Library Version: 2402 R1
Documentation generated by doxygen
Loading...
Searching...
No Matches
singleton.cpp
1// #################################################################################################
2// ALib C++ Library
3//
4// Copyright 2013-2024 A-Worx GmbH, Germany
5// Published under 'Boost Software License' (a free software license, see LICENSE.txt)
6// #################################################################################################
8
9#if !defined(ALIB_DOX)
10# if !defined(HPP_ALIB_SINGLETONS_SINGLETON)
12# endif
13
14# if !defined(HPP_ALIB_COMPATIBILITY_STD_TYPEINFO)
16# endif
17
18# if ALIB_FEAT_SINGLETON_MAPPED && ALIB_DEBUG
19# if !defined(HPP_ALIB_SINGLETONS_DBGSINGLETONS)
21# endif
22# if ALIB_STRINGS && !defined (HPP_ALIB_STRINGS_FORMAT)
24# endif
25# endif
26
27# if ALIB_STRINGS
28# if !defined (HPP_ALIB_STRINGS_ASTRING)
30# endif
31# endif
32
33# if ALIB_MONOMEM
34# if !defined(HPP_ALIB_MONOMEM_HASHMAP)
36# endif
37# if !defined(HPP_ALIB_MONOMEM_HASHSET)
39# endif
40# else
41# if !defined(_GLIBCXX_UNORDERED_MAP) && !defined(_UNORDERED_MAP_)
42# include <unordered_map>
43# endif
44# if !defined (_GLIBCXX_MUTEX) && !defined(_MUTEX_)
45# include <mutex>
46# endif
47# if !defined (_GLIBCXX_CSTRING) && !defined(_CSTRING_)
48# include <cstring>
49# endif
50# endif
51
52#endif // !defined(ALIB_DOX)
53
54namespace alib {
55
56#if ALIB_FEAT_SINGLETON_MAPPED && !defined(ALIB_DOX)
57namespace { bool inShutdown= false; }
58#endif
59/**
60 * This is the namespace of \alibmod <b>"Singletons"</b>. Please refer to the
61 * \ref alib_mod_singletons "Programmer's Manual Of ALib Singletons" for information about
62 * using this (single :-) \b %Singleton class in this tiny namespace.
63 */
64namespace singletons {
65
66
67#if ALIB_FEAT_SINGLETON_MAPPED && !defined(ALIB_DOX)
68
69#if ALIB_MONOMEM
70 extern ALIB_API HashMap <TypeFunctors::Key, void*,
71 TypeFunctors::Hash,
72 TypeFunctors::EqualTo > singletonMap;
74 TypeFunctors::Hash,
75 TypeFunctors::EqualTo > singletonMap(&monomem::GlobalAllocator);
76#else
77 extern ALIB_API std::unordered_map<TypeFunctors::Key, void*,
78 TypeFunctors::Hash,
79 TypeFunctors::EqualTo > singletonMap;
80 ALIB_API std::unordered_map<TypeFunctors::Key, void*,
81 TypeFunctors::Hash,
82 TypeFunctors::EqualTo > singletonMap;
83
85 extern std::recursive_mutex singletonLock;
86 std::recursive_mutex singletonLock; )
87#endif
88
89void storeSingleton( const std::type_info& type, void* theSingleton )
90{
91 #if ALIB_MONOMEM
92 if( singletonMap.Size() == 0)
93 {
94 singletonMap.MaxLoadFactor( 10 );
95 singletonMap.Reserve( 23, lang::ValueReference::Absolute );
96 }
97
98 singletonMap.EmplaceUnique( &type, theSingleton );
99
100 // we unlock now as we were locked in getSingleton
102 #else
103 if( singletonMap.size() == 0)
104 {
105 singletonMap.max_load_factor( 10 );
106 singletonMap.reserve( 23 );
107 }
108
109 singletonMap.emplace(&type, theSingleton);
110
111 // we unlock now as we were locked in getSingleton
112 ALIB_IF_THREADS( singletonLock.unlock(); )
113 #endif
114}
115
116void removeSingleton( const std::type_info& type )
117{
118 if( !inShutdown)
119 {
120 #if ALIB_MONOMEM
122 ALIB_ASSERT_RESULT_EQUALS( singletonMap.Erase(&type), 1)
123 monomem::ReleaseGlobalAllocator();
124 #else
125 ALIB_IF_THREADS( singletonLock.lock(); )
126 ALIB_ASSERT_RESULT_EQUALS( singletonMap.erase(&type), 1)
127 ALIB_IF_THREADS( singletonLock.unlock(); )
128 #endif
129 }
130}
131
132void* getSingleton ( const std::type_info& type )
133{
134 #if ALIB_MONOMEM
136 auto entry= singletonMap.Find( &type );
137 if ( entry != singletonMap.end() )
138 {
139 void* result= entry->second;
141 return result;
142 }
143
144 // Attn: we do not unlock when we have not found the singleton!
145 return nullptr;
146 #else
147 ALIB_IF_THREADS( singletonLock.lock(); )
148 auto entry= singletonMap.find( &type );
149 if ( entry != singletonMap.end() )
150 {
151 void* result= entry->second;
152 ALIB_IF_THREADS( singletonLock.unlock(); )
153 return result;
154 }
155
156 // Attn: we do not unlock when we have not found the singleton!
157 return nullptr;
158 #endif
159}
160
161
162#endif //ALIB_FEAT_SINGLETON_MAPPED
163
165{
166 #if ALIB_FEAT_SINGLETON_MAPPED
167 inShutdown= true;
168 for( auto mapPair : singletonMap)
169 {
170 Singleton<void*>* theSingleton;
171 memcpy( &theSingleton, &mapPair.second, sizeof(void*) );
172 delete theSingleton;
173 }
174 #endif
175}
176
177
178
179#if ALIB_DEBUG && ALIB_FEAT_SINGLETON_MAPPED
180 #if ALIB_MONOMEM
183 TypeFunctors::EqualTo >& DbgGetSingletons() { return singletonMap; }
184 #else
185 std::unordered_map<TypeFunctors::Key, void*,
187 TypeFunctors::EqualTo >& DbgGetSingletons() { return singletonMap; }
188 #endif
189
190 #if ALIB_STRINGS && ALIB_DEBUG
192 {
193 auto& types= DbgGetSingletons();
194 for( auto& it : types )
195 target << lang::DbgTypeDemangler(*it.first).Get()
196 << " = 0x" << NFormat::Hex(reinterpret_cast<uint64_t>(it.second) )
197 << NNewLine();
198
199 #if ALIB_MONOMEM
200 return static_cast<int>( types.Size() );
201 #else
202 return static_cast<int>( types.size() );
203 #endif
204 }
205 #endif
206#endif
207
208}} // namespace [alib::singletons]
ALIB_API const char * Get()
#define ALIB_ASSERT_RESULT_EQUALS( func, value)
Definition alib.hpp:999
#define ALIB_IF_THREADS(...)
Definition alib.hpp:303
#define ALIB_API
Definition alib.hpp:538
#define ALIB_CALLER_PRUNED
Definition alib.hpp:845
@ Absolute
Referring to an absolute value.
void ReleaseGlobalAllocator()
MonoAllocator GlobalAllocator(8 *1024)
MonoAllocator & AcquireGlobalAllocator(const NCString &dbgFile, int dbgLine, const NCString &dbgFunc)
ALIB_API HashMap< TypeFunctors::Key, void *, TypeFunctors::Hash, TypeFunctors::EqualTo > & DbgGetSingletons()
Definition alib.cpp:57
constexpr NCString NNewLine()
Definition cstring.hpp:540
monomem::HashMap< TKey, TMapped, THash, TEqual, THashCaching, TRecycling > HashMap
Type alias in namespace alib. See type definition alib::monomem::HashMap.
Definition hashmap.hpp:104