1 /*
2 Copyright (c) 2003, 2019, Oracle and/or its affiliates. All rights reserved.
3
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License, version 2.0,
6 as published by the Free Software Foundation.
7
8 This program is also distributed with certain software (including
9 but not limited to OpenSSL) that is licensed under separate terms,
10 as designated in a particular file or component or in included license
11 documentation. The authors of MySQL hereby grant you an additional
12 permission to link the program and your derivative works with the
13 separately licensed software that they have included with MySQL.
14
15 This program is distributed in the hope that it will be useful,
16 but WITHOUT ANY WARRANTY; without even the implied warranty of
17 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 GNU General Public License, version 2.0, for more details.
19
20 You should have received a copy of the GNU General Public License
21 along with this program; if not, write to the Free Software
22 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
23 */
24
25 #ifndef PROPERTIES_HPP
26 #define PROPERTIES_HPP
27
28 #include <ndb_global.h>
29 #include <BaseString.hpp>
30 #include <UtilBuffer.hpp>
31 #include <unordered_map>
32
33 enum PropertiesType {
34 PropertiesType_Undefined = -1,
35 PropertiesType_Uint32 = 0,
36 PropertiesType_char = 1,
37 PropertiesType_Properties = 2,
38 PropertiesType_Uint64 = 3
39 };
40
41 /**
42 * @struct Property
43 * @brief Stores one (name, value)-pair
44 *
45 * Value can be of type Properties, i.e. a Property may contain
46 * a Properties object.
47 */
48 struct Property {
49 Property(const char* name, Uint32 val);
50 Property(const char* name, Uint64 val);
51 Property(const char* name, const char * value);
52 Property(const char* name, const class Properties * value);
53 // We have no copy or move constructors so delete also assignment operator.
54 Property& operator=(const Property&) = delete;
55 Property& operator=(Property&&) = delete;
56 ~Property();
57 private:
58 friend class Properties;
59 struct PropertyImpl * impl;
60 };
61
62 /**
63 * @class Properties
64 * @brief Stores information in (name, value)-pairs
65 */
66 class Properties {
67 public:
68 static const char delimiter;
69 static const char version[];
70
71 Properties(bool case_insensitive= false);
72 Properties(const Properties &);
73 Properties(const Property *, int len);
74 Properties& operator=(const Properties&);
75 virtual ~Properties();
76
77 /**
78 * Set/Get wheather names in the Properties should be compared
79 * w/o case.
80 * NOTE: The property is automatically applied to all propoerties put
81 * into this after a called to setCaseInsensitiveNames has been made
82 * But properties already in when calling setCaseInsensitiveNames will
83 * not be affected
84 */
85 void setCaseInsensitiveNames(bool value);
86 bool getCaseInsensitiveNames() const;
87
88 /**
89 * Insert an array of value(s)
90 */
91 void put(const Property *, int len);
92
93 bool put(const char * name, Uint32 value, bool replace = false);
94 bool put64(const char * name, Uint64 value, bool replace = false);
95 bool put(const char * name, const char * value, bool replace = false);
96 bool put(const char * name, const Properties * value, bool replace = false);
97 bool append(const char * name, const char * value);
98
99 /**
100 * Same as put above,
101 * except that _%d (where %d is a number) is added to the name
102 * Compare get(name, no)
103 */
104 bool put(const char *, Uint32 no, Uint32, bool replace = false);
105 bool put64(const char *, Uint32 no, Uint64, bool replace = false);
106 bool put(const char *, Uint32 no, const char *, bool replace = false);
107 bool put(const char *, Uint32 no, const Properties *, bool replace = false);
108
109
110 bool getTypeOf(const char * name, PropertiesType * type) const;
111
112 /** @return true if Properties object contains name */
113 bool contains(const char * name) const;
114
115 bool get(const char * name, Uint32 * value) const;
116 bool get(const char * name, Uint64 * value) const;
117 bool get(const char * name, const char ** value) const;
118 bool get(const char * name, BaseString & value) const;
119 bool get(const char * name, const Properties ** value) const;
120
121 bool getCopy(const char * name, char ** value) const;
122 bool getCopy(const char * name, Properties ** value) const;
123
124 /**
125 * Same as get above
126 * except that _%d (where %d = no) is added to the name
127 */
128 bool getTypeOf(const char * name, Uint32 no, PropertiesType * type) const;
129 bool contains(const char * name, Uint32 no) const;
130
131 bool get(const char * name, Uint32 no, Uint32 * value) const;
132 bool get(const char * name, Uint32 no, Uint64 * value) const;
133 bool get(const char * name, Uint32 no, const char ** value) const;
134 bool get(const char * name, Uint32 no, const Properties ** value) const;
135
136 bool getCopy(const char * name, Uint32 no, char ** value) const;
137 bool getCopy(const char * name, Uint32 no, Properties ** value) const;
138
139 void clear();
140
141 void remove(const char * name);
142
143 void print(FILE * file = stdout, const char * prefix = 0) const;
144 /**
145 * Iterator over names
146 */
147 class Iterator
148 {
149 public:
150 Iterator(const Properties* prop);
151 ~Iterator();
152
153 const char* first();
154 const char* next();
155 private:
156 const Properties* m_prop;
157 class IteratorImpl *m_iterImpl;
158 };
159 friend class Properties::Iterator;
160
161 Uint32 getPackedSize() const;
162 bool unpack(const Uint32 * buf, Uint32 bufLen);
163 bool unpack(UtilBuffer &buf);
164
getPropertiesErrno() const165 Uint32 getPropertiesErrno() const { return propErrno; }
getOSErrno() const166 Uint32 getOSErrno() const { return osErrno; }
167
168 private:
169 Uint32 propErrno;
170 Uint32 osErrno;
171
172 friend class PropertiesImpl;
173 class PropertiesImpl * impl;
174 class Properties * parent;
175
176 void setErrno(Uint32 pErr, Uint32 osErr = 0) const ;
177 };
178
179 /**
180 * Error code for properties
181 */
182
183 /**
184 * No error
185 */
186 extern const Uint32 E_PROPERTIES_OK;
187
188 /**
189 * Invalid name in put, names can not contain Properties::delimiter
190 */
191 extern const Uint32 E_PROPERTIES_INVALID_NAME;
192
193 /**
194 * Element did not exist when using get
195 */
196 extern const Uint32 E_PROPERTIES_NO_SUCH_ELEMENT;
197
198 /**
199 * Element had wrong type when using get
200 */
201 extern const Uint32 E_PROPERTIES_INVALID_TYPE;
202
203 /**
204 * Element already existed when using put, and replace was not specified
205 */
206 extern const Uint32 E_PROPERTIES_ELEMENT_ALREADY_EXISTS;
207
208 /**
209 * Invalid version on properties file you are trying to read
210 */
211 extern const Uint32 E_PROPERTIES_INVALID_VERSION_WHILE_UNPACKING;
212
213 /**
214 * When unpacking an buffer
215 * found that buffer is to short
216 *
217 * Probably an invlaid buffer
218 */
219 extern const Uint32 E_PROPERTIES_INVALID_BUFFER_TO_SHORT;
220
221 /**
222 * Error when packing, can not allocate working buffer
223 *
224 * Note: OS error is set
225 */
226 extern const Uint32 E_PROPERTIES_ERROR_MALLOC_WHILE_PACKING;
227
228 /**
229 * Error when unpacking, can not allocate working buffer
230 *
231 * Note: OS error is set
232 */
233 extern const Uint32 E_PROPERTIES_ERROR_MALLOC_WHILE_UNPACKING;
234
235 /**
236 * Error when unpacking, invalid checksum
237 *
238 */
239 extern const Uint32 E_PROPERTIES_INVALID_CHECKSUM;
240
241 /**
242 * Error when unpacking
243 * No of items > 0 while size of buffer (left) <= 0
244 */
245 extern const Uint32 E_PROPERTIES_BUFFER_TO_SMALL_WHILE_UNPACKING;
246
247 inline bool
unpack(UtilBuffer & buf)248 Properties::unpack(UtilBuffer &buf) {
249 return unpack((const Uint32 *)buf.get_data(), buf.length());
250 }
251
252 #endif
253