ALib C++ Framework
by
Library Version: 2605 R0
Documentation generated by doxygen
Loading...
Searching...
No Matches
vmeta.hpp
Go to the documentation of this file.
1//==================================================================================================
2/// \file
3/// This header-file is part of module \alib_variables of the \aliblong.
4///
5/// Copyright 2013-2026 A-Worx GmbH, Germany.
6/// Published under #"mainpage_license".
7//==================================================================================================
8
10// forward declarations
11class Configuration;
13class Declaration;
14class Variable;
15
16/// Exception codes of namespace #"alib::variables;2".
17enum class Exceptions {
18 /// File not found when reading.
20
21 /// An error occurred writing the file .
23};
24}
25
27
28/// This struct is used as the reinterpretation type of generic pointers to ones reflecting
29/// the effective custom type of a configuration variable. While reinterpretation casts do not
30/// need such templated model, its use increases readability of the code.
31/// @tparam T The variable's data type.
32template<typename T>
33struct VData {
34 T custom; ///< The custom data that this object stores.
35
36 /// Reinterprets the <c>this</c>-pointer to a <c>VData<TReinterpret>*</c> and returns
37 /// member #".custom".
38 /// @tparam TReinterpret The type to reinterpret to.
39 /// @return A reference to the custom data.
40 template<typename TReinterpret> inline TReinterpret& As()
41 { return reinterpret_cast< VData<TReinterpret>*>(this)->custom; }
42
43 /// Reinterprets the <c>this</c>-pointer to a <c>const VData<TReinterpret>*</c> and returns
44 /// member #".custom".
45 /// @tparam TReinterpret The type to reinterpret to.
46 /// @return A const reference to the custom data.
47 template<typename TReinterpret> inline const TReinterpret& As() const
48 { return reinterpret_cast<const VData<TReinterpret>*>(this)->custom; }
49};
50
51/// Convenience type definition for "invalid" data elements. This type is used everywhere as a
52/// generic pointer type, which is reinterpreted when to the target type, when needed.
54
55} //namespace [alib::variables::detail]
56
58
59/// Abstract, virtual struct which provides meta-information about types storable in the
60/// #"%StringTree" nodes of class #"Configuration". A pointer to a singleton of this
61/// type is stored together with a reinterpreted pointer to the custom data record.
62///
63/// To register a custom data type with the configuration system, this type has to inherited and
64/// all methods implemented. It is recommended to define custom derived types using macro
65/// #"ALIB_VARIABLES_DEFINE_TYPE".
66/// Derived types are to be registered with the configuration instance by invoking
67/// #"Configuration::RegisterType;*".
68///
69/// @see Chapter #"alib_variables_types_custom" of the Programmer's Manual of camp \alib_variables.
70struct VMeta {
71 /// Virtual empty destructor.
72 virtual ~VMeta() {}
73
74 /// Abstract virtual method. Descendants need to return the type name they care of.<br>
75 /// Types declared with macro #"ALIB_VARIABLES_DEFINE_TYPE" implement this method
76 /// rightfully.
77 /// @return The type's name.
78 virtual String typeName() const =0;
79
80 #if ALIB_DEBUG
81 /// Abstract virtual method. Descendants need to return the <c>std::type_info&</c> received
82 /// with <c>typeid()</c>. This method is available only in debug-compilations and is used
83 /// to assert that the correct types are read from declared variables.<br>
84 /// Types declared with macro #"ALIB_VARIABLES_DEFINE_TYPE" implement this method
85 /// rightfully.
86 /// @return The C++ type ID.
87 virtual const std::type_info& dbgTypeID() =0;
88 #endif
89
90 /// Abstract virtual method. Descendants need to return '<c>sizeof(T)</c>', with \p{T} being
91 /// the custom type. Types declared with macro #"ALIB_VARIABLES_DEFINE_TYPE" implement
92 /// this method rightfully. With that, it is also asserted that the alignment of the custom
93 /// type is not greater than '<c>alignof(uint64_t)</c>', respectively not greater than
94 /// what is specified with the configuration macro #"ALIB_MONOMEM_POOLALLOCATOR_DEFAULT_ALIGNMENT".
95 /// @return The size of the variable's content type.
96 virtual size_t size() =0;
97
98 /// Virtual method which returns \c false in its default version.
99 /// Descendants may return \c true, if the values should automatically be written back to
100 /// configuration data sources, if such sources support this.
101 /// Of course, instead of returning a fixed value, implementations may also return a value
102 /// stored in the given \p{data} struct.<br>
103 /// The value can be requested with method #"Variable::IsWriteBack;*".
104 /// The macro #"ALIB_VARIABLES_DEFINE_TYPE" is not enabled to override this method.
105 /// Hence, variables that should support this flag, need to define their type without
106 /// the help of this macro.
107 /// @see Class #"IniFileFeeder" acknowledges and supports this flag.
108 /// @param data A pointer to the user data struct.
109 /// @return \c true if configuration systems should write values of this variable back.
110 virtual bool isWriteBack(detail::VDATA* data) const { (void) data; return false; }
111
112 /// Abstract virtual method. Descendants need to construct a custom instance at the given
113 /// \p{memory}. This is done using a "placement-new" as follows:
114 ///
115 /// new (memory) MyType();
116 ///
117 /// The pool allocator is \b not provided to allocate the custom type itself (this was already
118 /// done before calling this method). Instead, it may be used to allocate members
119 /// in the custom type. It may also be passed to the instance for further use during it's
120 /// lifecycle. However, in this case chapter #"alib_variables_multithreading" of the
121 /// Programmer's Manual has to be considered.
122 /// @param memory The pointer to the object of custom type.
123 /// @param pool The object pool of the configuration. May be used to dispose pool objects.
124 virtual void construct(detail::VDATA* memory, PoolAllocator& pool) =0;
125
126 /// Abstract virtual method. Descendants need to destruct a custom instance at the given
127 /// \p{memory}. This is done by calling the destructor as follows:
128 ///
129 /// reinterpret_cast<MyTypeName*>(memory)->~MyTypeName();
130 ///
131 /// The pool allocator is \b not provided to free the custom type itself (this will be done
132 /// automatically right after the call to this method). Instead, it may be used to free
133 /// members of the type, which had been allocated during construction or during the use.
134 ///
135 /// \note
136 /// However, for most types included with \alib, for example, #"AStringPA", if used as a
137 /// member of the custom type, no special action need to be taken and it is sufficient to call
138 /// the destructor of the custom type. This is because these types take a copy of the pool on
139 /// construction and thus their destructor disposes allocated pool objects autonomously.
140 /// In other words, if only such members are used, then method \c construct has to be
141 /// implemented to pass the pool object to the members, but this method simply invokes the
142 /// destructor of the custom type as shown above.
143 ///
144 /// @param memory The place to construct the custom type at.
145 /// @param pool The object pool of the configuration. May be used to allocate pool objects.
146 virtual void destruct(detail::VDATA* memory, PoolAllocator& pool) =0;
147
148
149 /// Abstract virtual method. Descendants need to implement this method and de-serialize
150 /// (aka parse) the custom type from the given string value.
151 /// \attention
152 /// Types declared with macro #"ALIB_VARIABLES_DEFINE_TYPE" only declare this method.
153 /// An implementation needs to be provided in a compilation unit.
154 ///
155 /// @param data A pointer to the user type which is to be initialized.
156 /// @param cfg The configuration that holds the variable.
157 /// @param escaper An escaper to be used to convert external strings to C++ native strings.
158 /// @param src The source string to parse. This may be assigned to a value of type
159 /// #"TSubstring" which already provides simple parser mechanics.
160 /// Likewise, #"util::TTokenizer" might be an easy helper to be
161 /// used for parsing.
162 virtual void imPort( detail::VDATA* data, Configuration& cfg, const StringEscaper& escaper,
163 const String& src ) =0;
164
165 /// Abstract virtual method. Descendants need to implement this method. It is invoked when a
166 /// variable is written into an external configuration source (in this case 'drain') or
167 /// otherwise needs to be serialized.
168 ///
169 /// Note that export functions are allowed to add #"NEW_LINE" codes into the export string.
170 /// This allows external configuration systems to nicely format their entries, in case those
171 /// are human-readable. See chapter #"alib_variables_external_custom" of the Programmer's
172 /// Manual for more information.
173 ///
174 /// \attention
175 /// Types declared with macro #"ALIB_VARIABLES_DEFINE_TYPE" only declare this method.
176 /// An implementation needs to be provided in a compilation unit. Otherwise linking software
177 /// fails.
178 ///
179 /// @param data A pointer to the user type which is to be serialized.
180 /// @param cfg The configuration that holds the variable.
181 /// @param escaper An escaper to be used to escape strings.
182 /// @param dest The destination string. Must not be reset prior writing, but appended.
183 ///
184 virtual void exPort( detail::VDATA* data, Configuration& cfg, const StringEscaper& escaper,
185 AString& dest ) =0;
186};
187
188} // namespace [alib::variables]
189
190//==================================================================================================
191// ==== Built-in Types
192//==================================================================================================
194{
195/// Variable content type used with boolean type <c>"B"</c>. When this type is imported,
196/// the value is tried to be parsed with the tokens in
197/// #"Configuration::BooleanTokens;*". If successful, the index of the pair of
198/// <c>true/false</c>-tokens is stored in field #"TokenIndex". When exported back to
199/// a configuration file or otherwise serialized or printed, then the right human-readable
200/// term, corresponding to the potentially now different #"Value" is used.
201struct Bool {
202 /// The boolean value. Defaults to \c false.
203 bool Value =false;
204
205 /// The index in the #"Configuration::BooleanTokens;list of tokens" found when
206 /// imported from a string. Can also be set programmatically to force a certain output
207 /// "format". Defaults to \c -1 which indicates that the value was not parsed.
208 /// On exporting, when \c -1, index \c 0 is used.
209 int8_t TokenIndex =-1;
210
211 /// Assignment operator.
212 /// @param newValue The value to set.
213 /// @return The new value.
214 bool operator=(bool newValue) { return Value= newValue; }
215
216 /// Implicit cast operator to \c bool.
217 /// @return Returns the stored value.
218 operator bool() const { return Value; }
219};
220
221
222 /// Type definition used with configuration variables of type <c>"SV,"</c>, which stores a
223 /// string array, imported by parsing a comma-separated string list.
224 ///
225 /// \attention
226 /// When exported, #"NEW_LINE" codes are added after each comma. This allows external
227 /// configuration systems to smoothly format longer lists of values. However, the
228 /// new line codes usually have to be detected with writing and eliminated on import.
229 /// Built-in type #"IniFile" processes such codes correctly.
231
232 /// Type definition used with configuration variables of type <c>"SV;"</c>, which stores a
233 /// string array, imported by parsing a string list separated by character <c>';'</c>.
234 ///
235 /// \attention
236 /// When exported, #"NEW_LINE" codes are added after each semicolon. This allows external
237 /// configuration systems to smoothly format longer lists of values. However, the
238 /// new line codes usually have to be detected with writing and eliminated on import.
239 /// Built-in type #"IniFile" processes such codes correctly.
241
242} // namespace [alib::variables]
243
244
245
246
247#if !DOXYGEN
248namespace alib::variables::detail {
249
250
251struct VMeta_integer : public VMeta {
252 ALIB_DLL String typeName() const override { return A_CHAR("I"); }
254 ALIB_DLL const std::type_info& dbgTypeID() override { return typeid(integer); }
255)
256 ALIB_DLL void construct(VDATA* dest, PoolAllocator&) override { new (dest) integer(); }
257 ALIB_DLL void destruct (VDATA* , PoolAllocator&) override {}
258 ALIB_DLL size_t size() override { return sizeof(integer); }
259 ALIB_DLL void imPort( VDATA*, Configuration&, const StringEscaper&, const String& ) override;
260 ALIB_DLL void exPort( VDATA*, Configuration&, const StringEscaper&, AString& ) override;
261};
262
263struct VMeta_float : public VMeta {
264 ALIB_DLL String typeName() const override { return A_CHAR("F"); }
266 ALIB_DLL const std::type_info& dbgTypeID() override { return typeid(double); }
267)
268 ALIB_DLL void construct(VDATA* dest, PoolAllocator&) override { new (dest) double(); }
269 ALIB_DLL void destruct (VDATA* , PoolAllocator&) override {}
270 ALIB_DLL size_t size() override { return sizeof(double); }
271 ALIB_DLL void imPort( VDATA*, Configuration&, const StringEscaper&, const String& ) override;
272 ALIB_DLL void exPort( VDATA*, Configuration&, const StringEscaper&, AString& ) override;
273};
274
275struct VMeta_String : public VMeta {
276 ALIB_DLL String typeName() const override { return A_CHAR("S"); }
278 ALIB_DLL const std::type_info& dbgTypeID() override { return typeid(AStringPA); }
279)
280 ALIB_DLL void construct(VDATA* dest, PoolAllocator& pool) override
281 { new (dest) AStringPA(pool); }
282 ALIB_DLL void destruct (VDATA* dest, PoolAllocator&) override
283 { reinterpret_cast<AStringPA*>(dest)->~AStringPA(); }
284 ALIB_DLL size_t size() override { return sizeof(AStringPA); }
285 ALIB_DLL void imPort( VDATA*, Configuration&, const StringEscaper&, const String& ) override;
286 ALIB_DLL void exPort( VDATA*, Configuration&, const StringEscaper&, AString& ) override;
287};
288
289} //namespace [alib::variables::detail]
290
291
293ALIB_VARIABLES_DEFINE_TYPE( alib::boxing:: , Box , A_CHAR("BOX") )
294ALIB_VARIABLES_DEFINE_TYPE_WITH_POOL_CONSTRUCTOR( alib::variables::, StringVectorComma , A_CHAR("SV,") )
295ALIB_VARIABLES_DEFINE_TYPE_WITH_POOL_CONSTRUCTOR( alib::variables::, StringVectorSemicolon, A_CHAR("SV;") )
296
297#endif // DOXYGEN
#define ALIB_DLL
#define A_CHAR(STR)
#define ALIB_EXPORT
#define ALIB_DBG(...)
void typeName(const detail::VTable *vtable, AString &result)
VData< void * > VDATA
Definition vmeta.hpp:53
Exceptions
Exception codes of namespace #"alib::variables;2".
Definition vmeta.hpp:17
@ ErrorWritingFile
An error occurred writing the file .
Definition vmeta.hpp:22
@ ErrorOpeningFile
File not found when reading.
Definition vmeta.hpp:19
alib::StringVectorPA StringVectorSemicolon
Definition vmeta.hpp:240
alib::StringVectorPA StringVectorComma
Definition vmeta.hpp:230
Definition alox.cpp:14
strings::TAString< character, PoolAllocator > AStringPA
Type alias in namespace #"%alib".
variables::Configuration Configuration
Type alias in namespace #"%alib".
lang::integer integer
Type alias in namespace #"%alib".
Definition integers.hpp:149
monomem::TPoolAllocator< MonoAllocator > PoolAllocator
strings::util::TStringVector< character, PoolAllocator > StringVectorPA
Type alias in namespace #"%alib".
Definition vector.hpp:110
strings::util::StringEscaper StringEscaper
Type alias in namespace #"%alib".
Definition escaper.hpp:181
strings::TString< character > String
Type alias in namespace #"%alib".
Definition string.hpp:2165
strings::TAString< character, lang::HeapAllocator > AString
Type alias in namespace #"%alib".
bool Value
The boolean value. Defaults to false.
Definition vmeta.hpp:203
bool operator=(bool newValue)
Definition vmeta.hpp:214
virtual void construct(detail::VDATA *memory, PoolAllocator &pool)=0
virtual void destruct(detail::VDATA *memory, PoolAllocator &pool)=0
virtual size_t size()=0
virtual void exPort(detail::VDATA *data, Configuration &cfg, const StringEscaper &escaper, AString &dest)=0
virtual void imPort(detail::VDATA *data, Configuration &cfg, const StringEscaper &escaper, const String &src)=0
virtual ~VMeta()
Virtual empty destructor.
Definition vmeta.hpp:72
virtual const std::type_info & dbgTypeID()=0
virtual bool isWriteBack(detail::VDATA *data) const
Definition vmeta.hpp:110
virtual String typeName() const =0
const TReinterpret & As() const
Definition vmeta.hpp:47
#define ALIB_VARIABLES_DEFINE_TYPE_WITH_POOL_CONSTRUCTOR(Namespace, CPPName, CfgTypeString)
#define ALIB_VARIABLES_DEFINE_TYPE(Namespace, CPPName, CfgTypeString)