MySQL 9.5.0
Source Code Documentation
component_sys_var_service.h
Go to the documentation of this file.
1/* Copyright (c) 2017, 2025, Oracle and/or its affiliates.
2
3This program is free software; you can redistribute it and/or modify
4it under the terms of the GNU General Public License, version 2.0,
5as published by the Free Software Foundation.
6
7This program is designed to work with certain software (including
8but not limited to OpenSSL) that is licensed under separate terms,
9as designated in a particular file or component or in included license
10documentation. The authors of MySQL hereby grant you an additional
11permission to link the program and your derivative works with the
12separately licensed software that they have either included with
13the program or referenced in the documentation.
14
15This program is distributed in the hope that it will be useful,
16but WITHOUT ANY WARRANTY; without even the implied warranty of
17MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18GNU General Public License, version 2.0, for more details.
19
20You should have received a copy of the GNU General Public License
21along with this program; if not, write to the Free Software
22Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
23
24#ifndef COMPONENT_SYS_VAR_SERVICE_H
25#define COMPONENT_SYS_VAR_SERVICE_H
26
27#include <stddef.h>
28
30#include <nulls.h>
31
33
34/**
35 A utility class for the ENUM variables
36*/
37
38struct TYPE_LIB {
39 size_t count{0}; /* How many types */
40 const char *name{nullptr}; /* Name of typelib */
41 const char **type_names{nullptr};
42 unsigned int *type_lengths{nullptr};
43};
44
45class THD;
46struct SYS_VAR;
47#define MYSQL_THD THD *
48
49/**
50 Signature for the check function
51
52 This is called to check if the value supplied is valid and can be set
53 as a new variable value at that time.
54 It needs to extract the value supplied from the value API pointer.
55 Note that extracting this value can be expensive (e.g. a scalar subquery)
56 hence it should be done only once. This is why the result of this should
57 be stored into the save output parameter so that it can be further reused by
58 update() etc.
59 For a multi-variable SET statement the server will first call all of the
60 check functions and only if they all return success it will start calling the
61 update functions.
62 So the idea is that the update function should succeed no matter what.
63 And all the necessary checks should be done in the check function.
64 If you do not supply a check or update function the server will use the basic
65 ones to check e.g. min and max values for the integer types etc.
66
67 @param thd The thread handle to the current thread
68 @param var handle to the system variable definition
69 @param[out] save placeholder for the value. This should be cast according to
70 the type
71 @param value Interface to extract the actual parameter value.
72 @return status
73 @retval 0 success
74 @retval 1 failure
75
76 @sa mysql_sys_var_update_func, mysql_service_component_sys_variable_register_t
77*/
78typedef int (*mysql_sys_var_check_func)(MYSQL_THD thd, SYS_VAR *var, void *save,
79 struct st_mysql_value *value);
80
81/**
82 Signature for the update function
83
84 This is called to set the updated value into the var_ptr placeholder and
85 invoke any side effects that may stem from setting this system variable.
86
87 It receives the pre-calculated value (usually from
88 @ref mysql_sys_var_check_func) in the save pointer.
89 It needs to set it into the var_ptr pointer and invoke any side effects.
90
91 For a multi-variable SET statement the server will first call all of the
92 check functions and only if they all return success it will start calling the
93 update functions.
94 So the idea is that the update function should succeed no matter what.
95 And all the necessary checks should be done in the check function.
96 If you do not supply an update function the server will use the basic
97 one to set the value according to the variable's type.
98
99 @param thd The thread handle to the current thread
100 @param var handle to the system variable definition
101 @param[out] val_ptr placeholder for the value. Store save in here.
102 @param save The pre-calculated value from check.
103
104 @sa mysql_sys_var_check_func, mysql_service_component_sys_variable_register_t
105*/
107 void *val_ptr, const void *save);
108
109/**
110 @addtogroup group_components_services_sys_var_service_args Variable
111 definitions
112
113 You need to fill one of these in an pass it to the registration function.
114 The values are copied so this doesn't have to survive once the registration
115 call is done.
116 So usually it's done as an automatic variable in the stack.
117
118 Make sure to use the right one for your variable type.
119 See @ref group_components_services_sys_var_service_types for what to use
120 for the individual types.
121
122 @sa mysql_service_component_sys_variable_register service.
123
124 @{
125*/
126
127/**
128 Defines an integral placeholder to fill in with values and
129 pass to the registration function.
130
131 Make sure to fill in def_val, min_val, max_val and blk_sz.
132*/
133#define INTEGRAL_CHECK_ARG(type) \
134 struct type##_check_arg_s { \
135 type def_val; \
136 type min_val; \
137 type max_val; \
138 type blk_sz; \
139 }
140
141/**
142 Defines an @ref TYPE_LIB placeholder to fill in with values and
143 pass to the registration function.
144
145 Make sure to fill in def_val and typelib.
146*/
147#define ENUM_CHECK_ARG(type) \
148 struct type##_check_arg_s { \
149 unsigned long def_val; \
150 TYPE_LIB *typelib; \
151 }
152
153/**
154 Defines a bool placeholder to fill in with values and
155 pass to the registration function.
156
157 Make sure to fill in def_val.
158*/
159#define BOOL_CHECK_ARG(type) \
160 struct type##_check_arg_s { \
161 bool def_val; \
162 }
163
164/**
165 Defines a char * placeholder to fill in with values and
166 pass to the registration function.
167
168 Make sure to fill in def_val.
169*/
170#define STR_CHECK_ARG(type) \
171 struct type##_check_arg_s { \
172 char *def_val; \
173 }
174/** @} */
175
176/**
177 @ingroup group_components_services_inventory
178
179 Service to register variable and get variable value
180
181 @sa mysql_component_sys_variable_imp
182*/
183BEGIN_SERVICE_DEFINITION(component_sys_variable_register)
184
185/**
186 Register a new system variable.
187
188 The variable registered is then accessible in SQL as "SELECT
189 component_name.name" The variable registration needs a global of the relevant
190 type that stores the value.
191
192 To define a new variable you need to:
193 1. Decide on a variable type among one of the
194 @ref group_components_services_sys_var_service_types
195 2. Decide on attributes of the type among one of the
196 @ref group_components_services_sys_var_service_flags
197 3. Declare a local variable placeholder matching the type using one of the
198 @ref group_components_services_sys_var_service_args macros.
199 4. Fill in the placeholder values (min, max, default etc) as appropriate for
200 the selected type.
201 5. Provide storage for the variable value: usually a global variable of the
202 relevant type.
203 6. Call the function with all of the above to register the system variable.
204
205 @warning: Make sure to unregister the system variable when you no longer
206 intend to have it or when your component deinitializes. Failure to do so will
207 lead to resource leaks and crashes. This doesn't apply to @ref
208 PLUGIN_VAR_NOSYSVAR variables! No need to unregister these.
209
210 Typical use
211 @code
212 static int int_variable_value;
213 static char *str_variable_value;
214 static ulong enum_variable_value;
215
216 static const char *enums[] = {"LOW", "MEDIUM", "STRONG", NullS};
217
218 static TYPE_LIB enums_typelib_t = {array_elements(enums) - 1,
219 "enums_typelib_t",
220 enums, NULL};
221
222 ...
223
224 INTEGRAL_CHECK_ARG(int) int_arg;
225 int_arg.def_val = 8;
226 int_arg.min_val = 0;
227 int_arg.max_val = 1024;
228 int_arg.blk_sz = 0;
229 if (mysql_service_component_sys_variable_register->register_variable(
230 "foo", "int_sys_var", PLUGIN_VAR_INT,
231 "Registering int sys_variable", NULL, NULL, (void *)&int_arg,
232 (void *)&int_variable_value)) {
233 deal_with_error();
234 }
235
236 STR_CHECK_ARG(str) str_arg;
237 str_arg.def_val = NULL;
238 if (mysql_service_component_sys_variable_register->register_variable(
239 "foo", "str_sys_var", PLUGIN_VAR_STR | PLUGIN_VAR_MEMALLOC,
240 "Registering string sys_variable", NULL, NULL, (void *)&str_arg,
241 (void *)&str_variable_value)) {
242 deal_with_error();
243 }
244
245 ENUM_CHECK_ARG(enum) enum_arg;
246 enum_arg.def_val = 1; // medium
247 enum_arg.typelib = &enum_typelib_t;
248 if (mysql_service_component_sys_variable_register->register_variable(
249 "foo", "enum_sys_var", PLUGIN_VAR_ENUM,
250 "Registering enum sys_variable", NULL, NULL, (void *)&enum_arg,
251 (void *)&enum_variable_value)) {
252 deal_with_error();
253 }
254 @endcode
255
256
257 @sa mysql_service_component_sys_variable_unregister_t
258
259 @param component_name The name of the component the system variable belongs
260 to.
261 @param name The name of the variable.
262 @param flags one of @ref group_components_services_sys_var_service_types plus
263 zero or more of group_components_services_sys_var_service_flags
264 @param comment explanation of what the variable is to be shown in metadata
265 tables
266 @param check A function to be called to check for validity of the new value.
267 @param update A function to be called when the variable value is updated
268 @param check_arg The variable declared through one of
269 @ref group_components_services_sys_var_service_args
270 @param variable_value A pointer to a storage location of the relevant type.
271 @retval true operation failed
272 @retval false operation succeeded
273*/
275 (const char *component_name, const char *name, int flags,
276 const char *comment, mysql_sys_var_check_func check,
277 mysql_sys_var_update_func update, void *check_arg,
278 void *variable_value));
279/**
280 Fetches the global value of a system variable
281
282 Call this to get the global value of a variable. You can access both the
283 component variables (SELECT @@global.component_name.variable_name) and the
284 "legacy" system variables (SELECT @@global.variable_name) that are registered
285 by the server component.
286 To access the latter you need to pass "mysql_server" (lowercase) as a
287 component name.
288
289 A pointer to the value is returned into the val input/output argument. And the
290 length of the value (as applicable) is returned into the out_length_of_val
291 argument.
292
293 In case when the user buffer was too small to copy the value, the call fails
294 and needed buffer size is returned by 'out_length_of_val'.
295
296 Typical use (char * variable):
297 @code
298
299 char *value, buffer_for_value[160];
300 size_t value_length;
301
302 value= &buffer_for_value[0];
303 value_length= sizeof(buffer_for_value) - 1;
304 get_variable("foo", "bar", &value, &value_length);
305
306 printf("%.*s", (int) value_length, value);
307 @endcode
308
309 @param component_name Name of the component or "mysql_server" for the legacy
310 ones.
311 @param name name of the variable
312 @param[in,out] val On input: a buffer to hold the value. On output a pointer
313 to the value.
314 @param[in,out] out_length_of_val On input: the buffer size. On output the
315 length of the data copied.
316
317 @retval true failure
318 @retval false success
319*/
320#if defined(__cplusplus) && (__cplusplus >= 201402L)
321[[deprecated("Use mysql_service_mysql_system_variable_reader->get() instead.")]]
322#endif
323DECLARE_BOOL_METHOD(get_variable, (const char *component_name, const char *name,
324 void **val, size_t *out_length_of_val));
325
326END_SERVICE_DEFINITION(component_sys_variable_register)
327
328/**
329 @ingroup group_components_services_inventory
330
331 Service to unregister variable
332
333 Make sure to call this for each variable registered.
334
335 @sa mysql_service_component_sys_variable_unregister_t
336*/
337BEGIN_SERVICE_DEFINITION(component_sys_variable_unregister)
338
340 (const char *component_name, const char *name));
341
342END_SERVICE_DEFINITION(component_sys_variable_unregister)
343
344#endif /* COMPONENT_SYS_VAR_SERVICE_H */
For each client connection we create a separate thread with THD serving as a thread/connection descri...
Definition: sql_lexer_thd.h:36
#define MYSQL_THD
Definition: component_sys_var_service.h:47
int(* mysql_sys_var_check_func)(MYSQL_THD thd, SYS_VAR *var, void *save, struct st_mysql_value *value)
Signature for the check function.
Definition: component_sys_var_service.h:78
void(* mysql_sys_var_update_func)(MYSQL_THD thd, SYS_VAR *var, void *val_ptr, const void *save)
Signature for the update function.
Definition: component_sys_var_service.h:106
static int flags[50]
Definition: hp_test1.cc:40
static user_var_entry * get_variable(THD *thd, const Name_string &name, const CHARSET_INFO *cs)
Get variable with given name; conditionally create it if non-existing.
Definition: item_func.cc:6093
#define comment
Definition: lexyy.cc:959
static uint update
Definition: myisamlog.cc:94
mysql_service_status_t unregister_variable(SHOW_VAR *) noexcept
Definition: components.cc:59
mysql_service_status_t register_variable(SHOW_VAR *) noexcept
Definition: components.cc:55
ValueType value(const std::optional< ValueType > &v)
Definition: gtid.h:83
#define END_SERVICE_DEFINITION(name)
A macro to end the last Service definition started with the BEGIN_SERVICE_DEFINITION macro.
Definition: service.h:91
#define BEGIN_SERVICE_DEFINITION(name)
Declares a new Service.
Definition: service.h:86
#define DECLARE_BOOL_METHOD(name, args)
Declares a method that returns bool as a part of the Service definition.
Definition: service.h:112
case opt name
Definition: sslopt-case.h:29
Definition: system_variables_bits.h:153
A utility class for the ENUM variables.
Definition: component_sys_var_service.h:38
const char * name
Definition: component_sys_var_service.h:40
unsigned int * type_lengths
Definition: component_sys_var_service.h:42
size_t count
Definition: component_sys_var_service.h:39
const char ** type_names
Definition: component_sys_var_service.h:41
Definition: system_variables_bits.h:96